Fix linking MSP430 files created by gcc's LTO optimizer.
[deliverable/binutils-gdb.git] / bfd / pdp11.c
CommitLineData
e135f41b 1/* BFD back-end for PDP-11 a.out binaries.
219d1afa 2 Copyright (C) 2001-2018 Free Software Foundation, Inc.
e135f41b 3
42ef282f 4 This file is part of BFD, the Binary File Descriptor library.
e135f41b 5
42ef282f
NC
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
cd123cb7 8 the Free Software Foundation; either version 3 of the License, or
42ef282f 9 (at your option) any later version.
e135f41b 10
42ef282f
NC
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
e135f41b 15
42ef282f
NC
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
cd123cb7
NC
18 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
19 MA 02110-1301, USA. */
20
e135f41b
NC
21
22/* BFD backend for PDP-11, running 2.11BSD in particular.
23
24 This file was hacked up by looking hard at the existing vaxnetbsd
25 back end and the header files in 2.11BSD.
26
27 TODO
28 * support for V7 file formats
29 * support for overlay object files (see 2.11 a.out(5))
30 * support for old and very old archives
31 (see 2.11 ar(5), historical section)
dc810e39 32
e135f41b
NC
33 Search for TODO to find other areas needing more work. */
34
35#define BYTES_IN_WORD 2
36#define BYTES_IN_LONG 4
37#define ARCH_SIZE 16
38#undef TARGET_IS_BIG_ENDIAN_P
39
11b8aeb8 40#define TARGET_PAGE_SIZE 256
e135f41b
NC
41#define SEGMENT__SIZE TARGET_PAGE_SIZE
42
43#define DEFAULT_ARCH bfd_arch_pdp11
07d6d2b8 44#define DEFAULT_MID M_PDP11
e135f41b 45
e43d48cc
AM
46/* Do not "beautify" the CONCAT* macro args. Traditional C will not
47 remove whitespace added here, and thus will fail to concatenate
48 the tokens. */
49#define MY(OP) CONCAT2 (pdp11_aout_,OP)
50
e135f41b
NC
51/* This needs to start with a.out so GDB knows it is an a.out variant. */
52#define TARGETNAME "a.out-pdp11"
53
54/* This is the normal load address for executables. */
55#define TEXT_START_ADDR 0
56
57/* The header is not included in the text segment. */
58#define N_HEADER_IN_TEXT(x) 0
59
e135f41b 60/* There is no flags field. */
bbb1afc8 61#define N_FLAGS(execp) 0
e135f41b 62
bbb1afc8 63#define N_SET_FLAGS(execp, flags) do { } while (0)
a77e83b7
AM
64#define N_BADMAG(x) (N_MAGIC(x) != OMAGIC \
65 && N_MAGIC(x) != NMAGIC \
66 && N_MAGIC(x) != ZMAGIC)
e135f41b 67
3db64b00 68#include "sysdep.h"
e135f41b
NC
69#include "bfd.h"
70
71#define external_exec pdp11_external_exec
72struct pdp11_external_exec
116c20d2
NC
73{
74 bfd_byte e_info[2]; /* Magic number. */
75 bfd_byte e_text[2]; /* Length of text section in bytes. */
76 bfd_byte e_data[2]; /* Length of data section in bytes. */
77 bfd_byte e_bss[2]; /* Length of bss area in bytes. */
78 bfd_byte e_syms[2]; /* Length of symbol table in bytes. */
79 bfd_byte e_entry[2]; /* Start address. */
80 bfd_byte e_unused[2]; /* Not used. */
81 bfd_byte e_flag[2]; /* Relocation info stripped. */
07d6d2b8 82 bfd_byte e_relocatable; /* Ugly hack. */
116c20d2 83};
e135f41b
NC
84
85#define EXEC_BYTES_SIZE (8 * 2)
86
87#define A_MAGIC1 OMAGIC
88#define OMAGIC 0407 /* ...object file or impure executable. */
89#define A_MAGIC2 NMAGIC
116c20d2
NC
90#define NMAGIC 0410 /* Pure executable. */
91#define ZMAGIC 0413 /* Demand-paged executable. */
92#define A_MAGIC3 0411 /* Separated I&D. */
93#define A_MAGIC4 0405 /* Overlay. */
94#define A_MAGIC5 0430 /* Auto-overlay (nonseparate). */
95#define A_MAGIC6 0431 /* Auto-overlay (separate). */
e135f41b
NC
96#define QMAGIC 0
97#define BMAGIC 0
98
99#define A_FLAG_RELOC_STRIPPED 0x0001
100
101#define external_nlist pdp11_external_nlist
102struct pdp11_external_nlist
116c20d2
NC
103{
104 bfd_byte e_unused[2]; /* Unused. */
105 bfd_byte e_strx[2]; /* Index into string table of name. */
106 bfd_byte e_type[1]; /* Type of symbol. */
107 bfd_byte e_ovly[1]; /* Overlay number. */
108 bfd_byte e_value[2]; /* Value of symbol. */
109};
e135f41b
NC
110
111#define EXTERNAL_NLIST_SIZE 8
112
113#define N_TXTOFF(x) (EXEC_BYTES_SIZE)
bbb1afc8
AM
114#define N_DATOFF(x) (N_TXTOFF(x) + (x)->a_text)
115#define N_TRELOFF(x) (N_DATOFF(x) + (x)->a_data)
116#define N_DRELOFF(x) (N_TRELOFF(x) + (x)->a_trsize)
117#define N_SYMOFF(x) (N_DRELOFF(x) + (x)->a_drsize)
118#define N_STROFF(x) (N_SYMOFF(x) + (x)->a_syms)
e135f41b
NC
119
120#define WRITE_HEADERS(abfd, execp) pdp11_aout_write_headers (abfd, execp)
121
e135f41b
NC
122#include "libbfd.h"
123#include "libaout.h"
124
125#define SWAP_MAGIC(ext) bfd_getl16 (ext)
126
127#define MY_entry_is_text_address 1
128
129#define MY_write_object_contents MY(write_object_contents)
116c20d2 130static bfd_boolean MY(write_object_contents) (bfd *);
e135f41b
NC
131#define MY_text_includes_header 1
132
e135f41b
NC
133#define MY_BFD_TARGET
134
135#include "aout-target.h"
136
116c20d2 137/* Start of modified aoutx.h. */
e135f41b
NC
138#define KEEPIT udata.i
139
116c20d2 140#include <string.h> /* For strchr and friends. */
e135f41b
NC
141#include "bfd.h"
142#include "sysdep.h"
3882b010 143#include "safe-ctype.h"
e135f41b
NC
144#include "bfdlink.h"
145
146#include "libaout.h"
e135f41b
NC
147#include "aout/aout64.h"
148#include "aout/stab_gnu.h"
149#include "aout/ar.h"
150
151#undef N_TYPE
152#undef N_UNDF
153#undef N_ABS
154#undef N_TEXT
155#undef N_DATA
156#undef N_BSS
157#undef N_REG
158#undef N_FN
159#undef N_EXT
116c20d2
NC
160#define N_TYPE 0x1f /* Type mask. */
161#define N_UNDF 0x00 /* Undefined. */
162#define N_ABS 0x01 /* Absolute. */
163#define N_TEXT 0x02 /* Text segment. */
164#define N_DATA 0x03 /* Data segment. */
165#define N_BSS 0x04 /* Bss segment. */
166#define N_REG 0x14 /* Register symbol. */
167#define N_FN 0x1f /* File name. */
168#define N_EXT 0x20 /* External flag. */
e135f41b
NC
169
170#define RELOC_SIZE 2
171
116c20d2
NC
172#define RELFLG 0x0001 /* PC-relative flag. */
173#define RTYPE 0x000e /* Type mask. */
174#define RIDXMASK 0xfff0 /* Index mask. */
e135f41b 175
116c20d2
NC
176#define RABS 0x00 /* Absolute. */
177#define RTEXT 0x02 /* Text. */
178#define RDATA 0x04 /* Data. */
179#define RBSS 0x06 /* Bss. */
180#define REXT 0x08 /* External. */
e135f41b
NC
181
182#define RINDEX(x) (((x) & 0xfff0) >> 4)
183
e135f41b
NC
184#ifndef MY_final_link_relocate
185#define MY_final_link_relocate _bfd_final_link_relocate
186#endif
187
188#ifndef MY_relocate_contents
189#define MY_relocate_contents _bfd_relocate_contents
190#endif
191
116c20d2
NC
192/* A hash table used for header files with N_BINCL entries. */
193
194struct aout_link_includes_table
195{
196 struct bfd_hash_table root;
197};
198
199/* A linked list of totals that we have found for a particular header
200 file. */
201
202struct aout_link_includes_totals
203{
204 struct aout_link_includes_totals *next;
205 bfd_vma total;
206};
207
208/* An entry in the header file hash table. */
209
210struct aout_link_includes_entry
211{
212 struct bfd_hash_entry root;
213 /* List of totals we have found for this file. */
214 struct aout_link_includes_totals *totals;
215};
216
217/* During the final link step we need to pass around a bunch of
218 information, so we do it in an instance of this structure. */
219
220struct aout_final_link_info
221{
222 /* General link information. */
223 struct bfd_link_info *info;
224 /* Output bfd. */
225 bfd *output_bfd;
226 /* Reloc file positions. */
227 file_ptr treloff, dreloff;
228 /* File position of symbols. */
229 file_ptr symoff;
230 /* String table. */
231 struct bfd_strtab_hash *strtab;
232 /* Header file hash table. */
233 struct aout_link_includes_table includes;
234 /* A buffer large enough to hold the contents of any section. */
235 bfd_byte *contents;
236 /* A buffer large enough to hold the relocs of any section. */
237 void * relocs;
238 /* A buffer large enough to hold the symbol map of any input BFD. */
239 int *symbol_map;
240 /* A buffer large enough to hold output symbols of any input BFD. */
241 struct external_nlist *output_syms;
242};
243
e135f41b
NC
244reloc_howto_type howto_table_pdp11[] =
245{
07d6d2b8 246 /* type rs size bsz pcrel bitpos ovrf sf name part_inpl readmask setmask pcdone */
b34976b6
AM
247HOWTO( 0, 0, 1, 16, FALSE, 0, complain_overflow_signed,0,"16", TRUE, 0x0000ffff,0x0000ffff, FALSE),
248HOWTO( 1, 0, 1, 16, TRUE, 0, complain_overflow_signed,0,"DISP16", TRUE, 0x0000ffff,0x0000ffff, FALSE),
e135f41b
NC
249};
250
251#define TABLE_SIZE(TABLE) (sizeof(TABLE)/sizeof(TABLE[0]))
252
116c20d2 253
13e570f8 254static bfd_boolean aout_link_check_archive_element (bfd *, struct bfd_link_info *, struct bfd_link_hash_entry *, const char *, bfd_boolean *);
07d6d2b8
AM
255static bfd_boolean aout_link_add_object_symbols (bfd *, struct bfd_link_info *);
256static bfd_boolean aout_link_add_symbols (bfd *, struct bfd_link_info *);
257static bfd_boolean aout_link_write_symbols (struct aout_final_link_info *, bfd *);
116c20d2
NC
258
259
e135f41b 260reloc_howto_type *
116c20d2
NC
261NAME (aout, reloc_type_lookup) (bfd * abfd ATTRIBUTE_UNUSED,
262 bfd_reloc_code_real_type code)
e135f41b
NC
263{
264 switch (code)
265 {
266 case BFD_RELOC_16:
267 return &howto_table_pdp11[0];
268 case BFD_RELOC_16_PCREL:
269 return &howto_table_pdp11[1];
270 default:
116c20d2 271 return NULL;
e135f41b
NC
272 }
273}
274
157090f7
AM
275reloc_howto_type *
276NAME (aout, reloc_name_lookup) (bfd *abfd ATTRIBUTE_UNUSED,
277 const char *r_name)
278{
279 unsigned int i;
280
281 for (i = 0;
282 i < sizeof (howto_table_pdp11) / sizeof (howto_table_pdp11[0]);
283 i++)
284 if (howto_table_pdp11[i].name != NULL
285 && strcasecmp (howto_table_pdp11[i].name, r_name) == 0)
286 return &howto_table_pdp11[i];
287
288 return NULL;
289}
290
e135f41b 291static int
116c20d2 292pdp11_aout_write_headers (bfd *abfd, struct internal_exec *execp)
e135f41b
NC
293{
294 struct external_exec exec_bytes;
e135f41b
NC
295
296 if (adata(abfd).magic == undecided_magic)
3a8c4a5b 297 NAME (aout, adjust_sizes_and_vmas) (abfd);
e135f41b
NC
298
299 execp->a_syms = bfd_get_symcount (abfd) * EXTERNAL_NLIST_SIZE;
300 execp->a_entry = bfd_get_start_address (abfd);
301
116c20d2
NC
302 if (obj_textsec (abfd)->reloc_count > 0
303 || obj_datasec (abfd)->reloc_count > 0)
e135f41b
NC
304 {
305 execp->a_trsize = execp->a_text;
306 execp->a_drsize = execp->a_data;
307 }
308 else
309 {
310 execp->a_trsize = 0;
311 execp->a_drsize = 0;
312 }
313
116c20d2 314 NAME (aout, swap_exec_header_out) (abfd, execp, & exec_bytes);
e135f41b
NC
315
316 if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0)
b34976b6 317 return FALSE;
e135f41b 318
116c20d2 319 if (bfd_bwrite ((void *) &exec_bytes, (bfd_size_type) EXEC_BYTES_SIZE, abfd)
e135f41b 320 != EXEC_BYTES_SIZE)
b34976b6 321 return FALSE;
e135f41b 322
116c20d2
NC
323 /* Now write out reloc info, followed by syms and strings. */
324 if (bfd_get_outsymbols (abfd) != NULL
e135f41b
NC
325 && bfd_get_symcount (abfd) != 0)
326 {
bbb1afc8 327 if (bfd_seek (abfd, (file_ptr) (N_SYMOFF (execp)), SEEK_SET) != 0)
b34976b6 328 return FALSE;
e135f41b 329
116c20d2 330 if (! NAME (aout, write_syms) (abfd))
b34976b6 331 return FALSE;
e135f41b
NC
332 }
333
116c20d2
NC
334 if (obj_textsec (abfd)->reloc_count > 0
335 || obj_datasec (abfd)->reloc_count > 0)
e135f41b 336 {
bbb1afc8 337 if (bfd_seek (abfd, (file_ptr) (N_TRELOFF (execp)), SEEK_SET) != 0
116c20d2 338 || !NAME (aout, squirt_out_relocs) (abfd, obj_textsec (abfd))
bbb1afc8 339 || bfd_seek (abfd, (file_ptr) (N_DRELOFF (execp)), SEEK_SET) != 0
68ffbac6 340 || !NAME (aout, squirt_out_relocs) (abfd, obj_datasec (abfd)))
b34976b6 341 return FALSE;
e135f41b
NC
342 }
343
b34976b6 344 return TRUE;
dc810e39 345}
e135f41b
NC
346
347/* Write an object file.
348 Section contents have already been written. We write the
349 file header, symbols, and relocation. */
350
b34976b6 351static bfd_boolean
116c20d2 352MY(write_object_contents) (bfd *abfd)
e135f41b
NC
353{
354 struct internal_exec *execp = exec_hdr (abfd);
355
356 /* We must make certain that the magic number has been set. This
357 will normally have been done by set_section_contents, but only if
358 there actually are some section contents. */
359 if (! abfd->output_has_begun)
3a8c4a5b 360 NAME (aout, adjust_sizes_and_vmas) (abfd);
e135f41b
NC
361
362 obj_reloc_entry_size (abfd) = RELOC_SIZE;
363
116c20d2 364 return WRITE_HEADERS (abfd, execp);
e135f41b
NC
365}
366
116c20d2
NC
367/* Swap the information in an executable header @var{raw_bytes} taken
368 from a raw byte stream memory image into the internal exec header
369 structure "execp". */
e135f41b
NC
370
371#ifndef NAME_swap_exec_header_in
372void
116c20d2
NC
373NAME (aout, swap_exec_header_in) (bfd *abfd,
374 struct external_exec *bytes,
375 struct internal_exec *execp)
e135f41b 376{
e135f41b
NC
377 /* The internal_exec structure has some fields that are unused in this
378 configuration (IE for i960), so ensure that all such uninitialized
379 fields are zero'd out. There are places where two of these structs
116c20d2
NC
380 are memcmp'd, and thus the contents do matter. */
381 memset ((void *) execp, 0, sizeof (struct internal_exec));
e135f41b
NC
382 /* Now fill in fields in the execp, from the bytes in the raw data. */
383 execp->a_info = GET_MAGIC (abfd, bytes->e_info);
384 execp->a_text = GET_WORD (abfd, bytes->e_text);
385 execp->a_data = GET_WORD (abfd, bytes->e_data);
386 execp->a_bss = GET_WORD (abfd, bytes->e_bss);
387 execp->a_syms = GET_WORD (abfd, bytes->e_syms);
388 execp->a_entry = GET_WORD (abfd, bytes->e_entry);
389
390 if (GET_WORD (abfd, bytes->e_flag) & A_FLAG_RELOC_STRIPPED)
391 {
392 execp->a_trsize = 0;
393 execp->a_drsize = 0;
394 }
395 else
396 {
397 execp->a_trsize = execp->a_text;
398 execp->a_drsize = execp->a_data;
399 }
400}
116c20d2 401#define NAME_swap_exec_header_in NAME (aout, swap_exec_header_in)
e135f41b
NC
402#endif
403
116c20d2
NC
404/* Swap the information in an internal exec header structure
405 "execp" into the buffer "bytes" ready for writing to disk. */
e135f41b 406void
116c20d2
NC
407NAME (aout, swap_exec_header_out) (bfd *abfd,
408 struct internal_exec *execp,
409 struct external_exec *bytes)
e135f41b 410{
116c20d2 411 /* Now fill in fields in the raw data, from the fields in the exec struct. */
e135f41b
NC
412 PUT_MAGIC (abfd, execp->a_info, bytes->e_info);
413 PUT_WORD (abfd, execp->a_text, bytes->e_text);
414 PUT_WORD (abfd, execp->a_data, bytes->e_data);
415 PUT_WORD (abfd, execp->a_bss, bytes->e_bss);
416 PUT_WORD (abfd, execp->a_syms, bytes->e_syms);
417 PUT_WORD (abfd, execp->a_entry, bytes->e_entry);
418 PUT_WORD (abfd, 0, bytes->e_unused);
419
116c20d2
NC
420 if ((execp->a_trsize == 0 || execp->a_text == 0)
421 && (execp->a_drsize == 0 || execp->a_data == 0))
422 PUT_WORD (abfd, A_FLAG_RELOC_STRIPPED, bytes->e_flag);
423 else if (execp->a_trsize == execp->a_text
424 && execp->a_drsize == execp->a_data)
425 PUT_WORD (abfd, 0, bytes->e_flag);
e135f41b
NC
426 else
427 {
116c20d2 428 /* TODO: print a proper warning message. */
e135f41b
NC
429 fprintf (stderr, "BFD:%s:%d: internal error\n", __FILE__, __LINE__);
430 PUT_WORD (abfd, 0, bytes->e_flag);
431 }
432}
433
434/* Make all the section for an a.out file. */
435
b34976b6 436bfd_boolean
116c20d2 437NAME (aout, make_sections) (bfd *abfd)
e135f41b 438{
116c20d2 439 if (obj_textsec (abfd) == NULL && bfd_make_section (abfd, ".text") == NULL)
b34976b6 440 return FALSE;
116c20d2 441 if (obj_datasec (abfd) == NULL && bfd_make_section (abfd, ".data") == NULL)
b34976b6 442 return FALSE;
116c20d2 443 if (obj_bsssec (abfd) == NULL && bfd_make_section (abfd, ".bss") == NULL)
b34976b6
AM
444 return FALSE;
445 return TRUE;
e135f41b
NC
446}
447
116c20d2
NC
448/* Some a.out variant thinks that the file open in ABFD
449 checking is an a.out file. Do some more checking, and set up
450 for access if it really is. Call back to the calling
451 environment's "finish up" function just before returning, to
452 handle any last-minute setup. */
e135f41b
NC
453
454const bfd_target *
116c20d2
NC
455NAME (aout, some_aout_object_p) (bfd *abfd,
456 struct internal_exec *execp,
457 const bfd_target *(*callback_to_real_object_p) (bfd *))
e135f41b
NC
458{
459 struct aout_data_struct *rawptr, *oldrawptr;
460 const bfd_target *result;
dc810e39 461 bfd_size_type amt = sizeof (struct aout_data_struct);
e135f41b 462
116c20d2 463 rawptr = bfd_zalloc (abfd, amt);
e135f41b
NC
464 if (rawptr == NULL)
465 return 0;
466
467 oldrawptr = abfd->tdata.aout_data;
468 abfd->tdata.aout_data = rawptr;
469
dc12032b 470 /* Copy the contents of the old tdata struct. */
e135f41b
NC
471 if (oldrawptr != NULL)
472 *abfd->tdata.aout_data = *oldrawptr;
473
474 abfd->tdata.aout_data->a.hdr = &rawptr->e;
116c20d2 475 *(abfd->tdata.aout_data->a.hdr) = *execp; /* Copy in the internal_exec struct. */
e135f41b
NC
476 execp = abfd->tdata.aout_data->a.hdr;
477
116c20d2 478 /* Set the file flags. */
e135f41b
NC
479 abfd->flags = BFD_NO_FLAGS;
480 if (execp->a_drsize || execp->a_trsize)
481 abfd->flags |= HAS_RELOC;
116c20d2 482 /* Setting of EXEC_P has been deferred to the bottom of this function. */
e135f41b
NC
483 if (execp->a_syms)
484 abfd->flags |= HAS_LINENO | HAS_DEBUG | HAS_SYMS | HAS_LOCALS;
bbb1afc8 485 if (N_DYNAMIC (execp))
e135f41b
NC
486 abfd->flags |= DYNAMIC;
487
bbb1afc8 488 if (N_MAGIC (execp) == ZMAGIC)
e135f41b
NC
489 {
490 abfd->flags |= D_PAGED | WP_TEXT;
491 adata (abfd).magic = z_magic;
492 }
bbb1afc8 493 else if (N_MAGIC (execp) == NMAGIC)
e135f41b
NC
494 {
495 abfd->flags |= WP_TEXT;
496 adata (abfd).magic = n_magic;
497 }
bbb1afc8 498 else if (N_MAGIC (execp) == OMAGIC)
e135f41b
NC
499 adata (abfd).magic = o_magic;
500 else
501 {
502 /* Should have been checked with N_BADMAG before this routine
503 was called. */
504 abort ();
505 }
506
507 bfd_get_start_address (abfd) = execp->a_entry;
508
116c20d2 509 obj_aout_symbols (abfd) = NULL;
e135f41b
NC
510 bfd_get_symcount (abfd) = execp->a_syms / sizeof (struct external_nlist);
511
512 /* The default relocation entry size is that of traditional V7 Unix. */
513 obj_reloc_entry_size (abfd) = RELOC_SIZE;
514
116c20d2 515 /* The default symbol entry size is that of traditional Unix. */
e135f41b
NC
516 obj_symbol_entry_size (abfd) = EXTERNAL_NLIST_SIZE;
517
518#ifdef USE_MMAP
519 bfd_init_window (&obj_aout_sym_window (abfd));
520 bfd_init_window (&obj_aout_string_window (abfd));
521#endif
116c20d2 522
e135f41b
NC
523 obj_aout_external_syms (abfd) = NULL;
524 obj_aout_external_strings (abfd) = NULL;
525 obj_aout_sym_hashes (abfd) = NULL;
526
116c20d2 527 if (! NAME (aout, make_sections) (abfd))
e135f41b
NC
528 return NULL;
529
eea6121a
AM
530 obj_datasec (abfd)->size = execp->a_data;
531 obj_bsssec (abfd)->size = execp->a_bss;
e135f41b
NC
532
533 obj_textsec (abfd)->flags =
534 (execp->a_trsize != 0
535 ? (SEC_ALLOC | SEC_LOAD | SEC_CODE | SEC_HAS_CONTENTS | SEC_RELOC)
536 : (SEC_ALLOC | SEC_LOAD | SEC_CODE | SEC_HAS_CONTENTS));
537 obj_datasec (abfd)->flags =
538 (execp->a_drsize != 0
539 ? (SEC_ALLOC | SEC_LOAD | SEC_DATA | SEC_HAS_CONTENTS | SEC_RELOC)
540 : (SEC_ALLOC | SEC_LOAD | SEC_DATA | SEC_HAS_CONTENTS));
541 obj_bsssec (abfd)->flags = SEC_ALLOC;
542
543#ifdef THIS_IS_ONLY_DOCUMENTATION
544 /* The common code can't fill in these things because they depend
545 on either the start address of the text segment, the rounding
546 up of virtual addresses between segments, or the starting file
547 position of the text segment -- all of which varies among different
548 versions of a.out. */
549
550 /* Call back to the format-dependent code to fill in the rest of the
551 fields and do any further cleanup. Things that should be filled
552 in by the callback: */
e135f41b
NC
553 struct exec *execp = exec_hdr (abfd);
554
bbb1afc8 555 obj_textsec (abfd)->size = N_TXTSIZE (execp);
116c20d2 556 /* Data and bss are already filled in since they're so standard. */
e135f41b 557
116c20d2 558 /* The virtual memory addresses of the sections. */
bbb1afc8
AM
559 obj_textsec (abfd)->vma = N_TXTADDR (execp);
560 obj_datasec (abfd)->vma = N_DATADDR (execp);
561 obj_bsssec (abfd)->vma = N_BSSADDR (execp);
e135f41b 562
116c20d2 563 /* The file offsets of the sections. */
bbb1afc8
AM
564 obj_textsec (abfd)->filepos = N_TXTOFF (execp);
565 obj_datasec (abfd)->filepos = N_DATOFF (execp);
e135f41b 566
116c20d2 567 /* The file offsets of the relocation info. */
bbb1afc8
AM
568 obj_textsec (abfd)->rel_filepos = N_TRELOFF (execp);
569 obj_datasec (abfd)->rel_filepos = N_DRELOFF (execp);
e135f41b
NC
570
571 /* The file offsets of the string table and symbol table. */
bbb1afc8
AM
572 obj_str_filepos (abfd) = N_STROFF (execp);
573 obj_sym_filepos (abfd) = N_SYMOFF (execp);
e135f41b
NC
574
575 /* Determine the architecture and machine type of the object file. */
576 abfd->obj_arch = bfd_arch_obscure;
577
578 adata(abfd)->page_size = TARGET_PAGE_SIZE;
579 adata(abfd)->segment_size = SEGMENT_SIZE;
580 adata(abfd)->exec_bytes_size = EXEC_BYTES_SIZE;
581
582 return abfd->xvec;
583
584 /* The architecture is encoded in various ways in various a.out variants,
585 or is not encoded at all in some of them. The relocation size depends
586 on the architecture and the a.out variant. Finally, the return value
587 is the bfd_target vector in use. If an error occurs, return zero and
588 set bfd_error to the appropriate error code.
589
590 Formats such as b.out, which have additional fields in the a.out
591 header, should cope with them in this callback as well. */
116c20d2 592#endif /* DOCUMENTATION */
e135f41b
NC
593
594 result = (*callback_to_real_object_p)(abfd);
595
596 /* Now that the segment addresses have been worked out, take a better
597 guess at whether the file is executable. If the entry point
598 is within the text segment, assume it is. (This makes files
599 executable even if their entry point address is 0, as long as
600 their text starts at zero.).
601
602 This test had to be changed to deal with systems where the text segment
603 runs at a different location than the default. The problem is that the
604 entry address can appear to be outside the text segment, thus causing an
605 erroneous conclusion that the file isn't executable.
606
607 To fix this, we now accept any non-zero entry point as an indication of
608 executability. This will work most of the time, since only the linker
609 sets the entry point, and that is likely to be non-zero for most systems. */
610
611 if (execp->a_entry != 0
612 || (execp->a_entry >= obj_textsec(abfd)->vma
eea6121a 613 && execp->a_entry < obj_textsec(abfd)->vma + obj_textsec(abfd)->size))
e135f41b
NC
614 abfd->flags |= EXEC_P;
615#ifdef STAT_FOR_EXEC
616 else
617 {
618 struct stat stat_buf;
619
620 /* The original heuristic doesn't work in some important cases.
07d6d2b8
AM
621 The a.out file has no information about the text start
622 address. For files (like kernels) linked to non-standard
623 addresses (ld -Ttext nnn) the entry point may not be between
624 the default text start (obj_textsec(abfd)->vma) and
625 (obj_textsec(abfd)->vma) + text size. This is not just a mach
626 issue. Many kernels are loaded at non standard addresses. */
e135f41b
NC
627 if (abfd->iostream != NULL
628 && (abfd->flags & BFD_IN_MEMORY) == 0
629 && (fstat(fileno((FILE *) (abfd->iostream)), &stat_buf) == 0)
630 && ((stat_buf.st_mode & 0111) != 0))
631 abfd->flags |= EXEC_P;
632 }
633#endif /* STAT_FOR_EXEC */
634
0e71e495 635 if (!result)
e135f41b
NC
636 {
637 free (rawptr);
638 abfd->tdata.aout_data = oldrawptr;
639 }
640 return result;
641}
642
116c20d2 643/* Initialize ABFD for use with a.out files. */
e135f41b 644
b34976b6 645bfd_boolean
116c20d2 646NAME (aout, mkobject) (bfd *abfd)
e135f41b
NC
647{
648 struct aout_data_struct *rawptr;
dc810e39 649 bfd_size_type amt = sizeof (struct aout_data_struct);
e135f41b
NC
650
651 bfd_set_error (bfd_error_system_call);
652
116c20d2
NC
653 /* Use an intermediate variable for clarity. */
654 rawptr = bfd_zalloc (abfd, amt);
e135f41b
NC
655
656 if (rawptr == NULL)
b34976b6 657 return FALSE;
e135f41b
NC
658
659 abfd->tdata.aout_data = rawptr;
660 exec_hdr (abfd) = &(rawptr->e);
661
116c20d2
NC
662 obj_textsec (abfd) = NULL;
663 obj_datasec (abfd) = NULL;
664 obj_bsssec (abfd) = NULL;
e135f41b 665
b34976b6 666 return TRUE;
e135f41b
NC
667}
668
116c20d2
NC
669/* Keep track of machine architecture and machine type for
670 a.out's. Return the <<machine_type>> for a particular
671 architecture and machine, or <<M_UNKNOWN>> if that exact architecture
672 and machine can't be represented in a.out format.
e135f41b 673
116c20d2
NC
674 If the architecture is understood, machine type 0 (default)
675 is always understood. */
e135f41b
NC
676
677enum machine_type
116c20d2
NC
678NAME (aout, machine_type) (enum bfd_architecture arch,
679 unsigned long machine,
680 bfd_boolean *unknown)
e135f41b
NC
681{
682 enum machine_type arch_flags;
683
684 arch_flags = M_UNKNOWN;
b34976b6 685 *unknown = TRUE;
e135f41b
NC
686
687 switch (arch)
688 {
689 case bfd_arch_sparc:
690 if (machine == 0
691 || machine == bfd_mach_sparc
692 || machine == bfd_mach_sparc_sparclite
693 || machine == bfd_mach_sparc_v9)
694 arch_flags = M_SPARC;
695 else if (machine == bfd_mach_sparc_sparclet)
696 arch_flags = M_SPARCLET;
697 break;
698
e135f41b 699 case bfd_arch_i386:
250d94fd
AM
700 if (machine == 0
701 || machine == bfd_mach_i386_i386
702 || machine == bfd_mach_i386_i386_intel_syntax)
703 arch_flags = M_386;
e135f41b
NC
704 break;
705
e135f41b
NC
706 case bfd_arch_arm:
707 if (machine == 0) arch_flags = M_ARM;
708 break;
709
710 case bfd_arch_mips:
711 switch (machine)
712 {
713 case 0:
714 case 2000:
715 case bfd_mach_mips3000:
07d6d2b8 716 arch_flags = M_MIPS1;
e135f41b 717 break;
116c20d2 718 case bfd_mach_mips4000: /* MIPS3 */
e135f41b 719 case bfd_mach_mips4400:
116c20d2
NC
720 case bfd_mach_mips8000: /* MIPS4 */
721 case bfd_mach_mips6000: /* Real MIPS2: */
07d6d2b8 722 arch_flags = M_MIPS2;
e135f41b
NC
723 break;
724 default:
725 arch_flags = M_UNKNOWN;
726 break;
727 }
728 break;
729
730 case bfd_arch_ns32k:
731 switch (machine)
732 {
07d6d2b8 733 case 0: arch_flags = M_NS32532; break;
e135f41b
NC
734 case 32032: arch_flags = M_NS32032; break;
735 case 32532: arch_flags = M_NS32532; break;
736 default: arch_flags = M_UNKNOWN; break;
737 }
738 break;
739
740 case bfd_arch_pdp11:
741 /* TODO: arch_flags = M_PDP11; */
b34976b6 742 *unknown = FALSE;
e135f41b
NC
743 break;
744
745 case bfd_arch_vax:
b34976b6 746 *unknown = FALSE;
e135f41b 747 break;
dc810e39 748
e135f41b
NC
749 default:
750 arch_flags = M_UNKNOWN;
751 }
752
753 if (arch_flags != M_UNKNOWN)
b34976b6 754 *unknown = FALSE;
e135f41b
NC
755
756 return arch_flags;
757}
758
116c20d2
NC
759/* Set the architecture and the machine of the ABFD to the
760 values ARCH and MACHINE. Verify that @ABFD's format
761 can support the architecture required. */
e135f41b 762
b34976b6 763bfd_boolean
116c20d2
NC
764NAME (aout, set_arch_mach) (bfd *abfd,
765 enum bfd_architecture arch,
766 unsigned long machine)
e135f41b
NC
767{
768 if (! bfd_default_set_arch_mach (abfd, arch, machine))
b34976b6 769 return FALSE;
e135f41b
NC
770
771 if (arch != bfd_arch_unknown)
772 {
b34976b6 773 bfd_boolean unknown;
e135f41b 774
116c20d2 775 NAME (aout, machine_type) (arch, machine, &unknown);
e135f41b 776 if (unknown)
b34976b6 777 return FALSE;
e135f41b
NC
778 }
779
780 obj_reloc_entry_size (abfd) = RELOC_SIZE;
781
782 return (*aout_backend_info(abfd)->set_sizes) (abfd);
783}
784
785static void
116c20d2 786adjust_o_magic (bfd *abfd, struct internal_exec *execp)
e135f41b
NC
787{
788 file_ptr pos = adata (abfd).exec_bytes_size;
789 bfd_vma vma = 0;
790 int pad = 0;
791
792 /* Text. */
793 obj_textsec (abfd)->filepos = pos;
794 if (! obj_textsec (abfd)->user_set_vma)
795 obj_textsec (abfd)->vma = vma;
796 else
797 vma = obj_textsec (abfd)->vma;
798
eea6121a
AM
799 pos += obj_textsec (abfd)->size;
800 vma += obj_textsec (abfd)->size;
e135f41b
NC
801
802 /* Data. */
803 if (!obj_datasec (abfd)->user_set_vma)
804 {
eea6121a 805 obj_textsec (abfd)->size += pad;
e135f41b
NC
806 pos += pad;
807 vma += pad;
808 obj_datasec (abfd)->vma = vma;
809 }
810 else
811 vma = obj_datasec (abfd)->vma;
812 obj_datasec (abfd)->filepos = pos;
eea6121a
AM
813 pos += obj_datasec (abfd)->size;
814 vma += obj_datasec (abfd)->size;
e135f41b
NC
815
816 /* BSS. */
817 if (! obj_bsssec (abfd)->user_set_vma)
818 {
eea6121a 819 obj_datasec (abfd)->size += pad;
e135f41b
NC
820 pos += pad;
821 vma += pad;
822 obj_bsssec (abfd)->vma = vma;
823 }
824 else
825 {
08da05b0 826 /* The VMA of the .bss section is set by the VMA of the
07d6d2b8
AM
827 .data section plus the size of the .data section. We may
828 need to add padding bytes to make this true. */
e135f41b
NC
829 pad = obj_bsssec (abfd)->vma - vma;
830 if (pad > 0)
831 {
eea6121a 832 obj_datasec (abfd)->size += pad;
e135f41b
NC
833 pos += pad;
834 }
835 }
836 obj_bsssec (abfd)->filepos = pos;
837
838 /* Fix up the exec header. */
eea6121a
AM
839 execp->a_text = obj_textsec (abfd)->size;
840 execp->a_data = obj_datasec (abfd)->size;
841 execp->a_bss = obj_bsssec (abfd)->size;
bbb1afc8 842 N_SET_MAGIC (execp, OMAGIC);
e135f41b
NC
843}
844
845static void
116c20d2 846adjust_z_magic (bfd *abfd, struct internal_exec *execp)
e135f41b
NC
847{
848 bfd_size_type data_pad, text_pad;
849 file_ptr text_end;
dc810e39 850 const struct aout_backend_data *abdp;
e135f41b 851 int ztih; /* Nonzero if text includes exec header. */
dc810e39 852
e135f41b
NC
853 abdp = aout_backend_info (abfd);
854
855 /* Text. */
856 ztih = (abdp != NULL
857 && (abdp->text_includes_header
858 || obj_aout_subformat (abfd) == q_magic_format));
859 obj_textsec(abfd)->filepos = (ztih
860 ? adata(abfd).exec_bytes_size
861 : adata(abfd).zmagic_disk_block_size);
862 if (! obj_textsec(abfd)->user_set_vma)
863 {
864 /* ?? Do we really need to check for relocs here? */
865 obj_textsec(abfd)->vma = ((abfd->flags & HAS_RELOC)
866 ? 0
867 : (ztih
868 ? (abdp->default_text_vma
869 + adata (abfd).exec_bytes_size)
870 : abdp->default_text_vma));
871 text_pad = 0;
872 }
873 else
874 {
875 /* The .text section is being loaded at an unusual address. We
07d6d2b8
AM
876 may need to pad it such that the .data section starts at a page
877 boundary. */
e135f41b
NC
878 if (ztih)
879 text_pad = ((obj_textsec (abfd)->filepos - obj_textsec (abfd)->vma)
880 & (adata (abfd).page_size - 1));
881 else
882 text_pad = ((- obj_textsec (abfd)->vma)
883 & (adata (abfd).page_size - 1));
884 }
885
886 /* Find start of data. */
887 if (ztih)
888 {
eea6121a 889 text_end = obj_textsec (abfd)->filepos + obj_textsec (abfd)->size;
e135f41b
NC
890 text_pad += BFD_ALIGN (text_end, adata (abfd).page_size) - text_end;
891 }
892 else
893 {
894 /* Note that if page_size == zmagic_disk_block_size, then
895 filepos == page_size, and this case is the same as the ztih
896 case. */
eea6121a 897 text_end = obj_textsec (abfd)->size;
e135f41b
NC
898 text_pad += BFD_ALIGN (text_end, adata (abfd).page_size) - text_end;
899 text_end += obj_textsec (abfd)->filepos;
900 }
901
eea6121a 902 obj_textsec (abfd)->size += text_pad;
e135f41b
NC
903 text_end += text_pad;
904
905 /* Data. */
906 if (!obj_datasec(abfd)->user_set_vma)
907 {
908 bfd_vma vma;
eea6121a 909 vma = obj_textsec(abfd)->vma + obj_textsec(abfd)->size;
e135f41b
NC
910 obj_datasec(abfd)->vma = BFD_ALIGN (vma, adata(abfd).segment_size);
911 }
912 if (abdp && abdp->zmagic_mapped_contiguous)
913 {
914 text_pad = (obj_datasec(abfd)->vma
915 - obj_textsec(abfd)->vma
eea6121a
AM
916 - obj_textsec(abfd)->size);
917 obj_textsec(abfd)->size += text_pad;
e135f41b
NC
918 }
919 obj_datasec (abfd)->filepos = (obj_textsec (abfd)->filepos
eea6121a 920 + obj_textsec (abfd)->size);
dc810e39 921
e135f41b 922 /* Fix up exec header while we're at it. */
eea6121a 923 execp->a_text = obj_textsec(abfd)->size;
e135f41b
NC
924 if (ztih && (!abdp || (abdp && !abdp->exec_header_not_counted)))
925 execp->a_text += adata(abfd).exec_bytes_size;
bbb1afc8 926 N_SET_MAGIC (execp, ZMAGIC);
e135f41b
NC
927
928 /* Spec says data section should be rounded up to page boundary. */
eea6121a
AM
929 obj_datasec(abfd)->size
930 = align_power (obj_datasec(abfd)->size,
e135f41b 931 obj_bsssec(abfd)->alignment_power);
eea6121a 932 execp->a_data = BFD_ALIGN (obj_datasec(abfd)->size,
e135f41b 933 adata(abfd).page_size);
eea6121a 934 data_pad = execp->a_data - obj_datasec(abfd)->size;
e135f41b
NC
935
936 /* BSS. */
937 if (!obj_bsssec(abfd)->user_set_vma)
938 obj_bsssec(abfd)->vma = (obj_datasec(abfd)->vma
eea6121a 939 + obj_datasec(abfd)->size);
e135f41b
NC
940 /* If the BSS immediately follows the data section and extra space
941 in the page is left after the data section, fudge data
942 in the header so that the bss section looks smaller by that
943 amount. We'll start the bss section there, and lie to the OS.
944 (Note that a linker script, as well as the above assignment,
945 could have explicitly set the BSS vma to immediately follow
946 the data section.) */
947 if (align_power (obj_bsssec(abfd)->vma, obj_bsssec(abfd)->alignment_power)
eea6121a
AM
948 == obj_datasec(abfd)->vma + obj_datasec(abfd)->size)
949 execp->a_bss = (data_pad > obj_bsssec(abfd)->size) ? 0 :
950 obj_bsssec(abfd)->size - data_pad;
e135f41b 951 else
eea6121a 952 execp->a_bss = obj_bsssec(abfd)->size;
e135f41b
NC
953}
954
955static void
116c20d2 956adjust_n_magic (bfd *abfd, struct internal_exec *execp)
e135f41b
NC
957{
958 file_ptr pos = adata(abfd).exec_bytes_size;
959 bfd_vma vma = 0;
960 int pad;
dc810e39 961
e135f41b
NC
962 /* Text. */
963 obj_textsec(abfd)->filepos = pos;
964 if (!obj_textsec(abfd)->user_set_vma)
965 obj_textsec(abfd)->vma = vma;
966 else
967 vma = obj_textsec(abfd)->vma;
eea6121a
AM
968 pos += obj_textsec(abfd)->size;
969 vma += obj_textsec(abfd)->size;
e135f41b
NC
970
971 /* Data. */
972 obj_datasec(abfd)->filepos = pos;
973 if (!obj_datasec(abfd)->user_set_vma)
974 obj_datasec(abfd)->vma = BFD_ALIGN (vma, adata(abfd).segment_size);
975 vma = obj_datasec(abfd)->vma;
dc810e39 976
e135f41b 977 /* Since BSS follows data immediately, see if it needs alignment. */
eea6121a 978 vma += obj_datasec(abfd)->size;
e135f41b 979 pad = align_power (vma, obj_bsssec(abfd)->alignment_power) - vma;
eea6121a
AM
980 obj_datasec(abfd)->size += pad;
981 pos += obj_datasec(abfd)->size;
e135f41b
NC
982
983 /* BSS. */
984 if (!obj_bsssec(abfd)->user_set_vma)
985 obj_bsssec(abfd)->vma = vma;
986 else
987 vma = obj_bsssec(abfd)->vma;
988
989 /* Fix up exec header. */
eea6121a
AM
990 execp->a_text = obj_textsec(abfd)->size;
991 execp->a_data = obj_datasec(abfd)->size;
992 execp->a_bss = obj_bsssec(abfd)->size;
bbb1afc8 993 N_SET_MAGIC (execp, NMAGIC);
e135f41b
NC
994}
995
b34976b6 996bfd_boolean
3a8c4a5b 997NAME (aout, adjust_sizes_and_vmas) (bfd *abfd)
e135f41b
NC
998{
999 struct internal_exec *execp = exec_hdr (abfd);
1000
116c20d2 1001 if (! NAME (aout, make_sections) (abfd))
b34976b6 1002 return FALSE;
e135f41b
NC
1003
1004 if (adata(abfd).magic != undecided_magic)
b34976b6 1005 return TRUE;
e135f41b 1006
eea6121a
AM
1007 obj_textsec(abfd)->size =
1008 align_power(obj_textsec(abfd)->size,
e135f41b
NC
1009 obj_textsec(abfd)->alignment_power);
1010
e135f41b
NC
1011 /* Rule (heuristic) for when to pad to a new page. Note that there
1012 are (at least) two ways demand-paged (ZMAGIC) files have been
1013 handled. Most Berkeley-based systems start the text segment at
1014 (TARGET_PAGE_SIZE). However, newer versions of SUNOS start the text
1015 segment right after the exec header; the latter is counted in the
1016 text segment size, and is paged in by the kernel with the rest of
1017 the text. */
1018
1019 /* This perhaps isn't the right way to do this, but made it simpler for me
1020 to understand enough to implement it. Better would probably be to go
1021 right from BFD flags to alignment/positioning characteristics. But the
1022 old code was sloppy enough about handling the flags, and had enough
1023 other magic, that it was a little hard for me to understand. I think
1024 I understand it better now, but I haven't time to do the cleanup this
1025 minute. */
1026
1027 if (abfd->flags & WP_TEXT)
1028 adata(abfd).magic = n_magic;
1029 else
1030 adata(abfd).magic = o_magic;
1031
1032#ifdef BFD_AOUT_DEBUG /* requires gcc2 */
1033#if __GNUC__ >= 2
1034 fprintf (stderr, "%s text=<%x,%x,%x> data=<%x,%x,%x> bss=<%x,%x,%x>\n",
1035 ({ char *str;
1036 switch (adata(abfd).magic) {
1037 case n_magic: str = "NMAGIC"; break;
1038 case o_magic: str = "OMAGIC"; break;
1039 case z_magic: str = "ZMAGIC"; break;
1040 default: abort ();
1041 }
1042 str;
1043 }),
eea6121a 1044 obj_textsec(abfd)->vma, obj_textsec(abfd)->size,
07d6d2b8 1045 obj_textsec(abfd)->alignment_power,
eea6121a 1046 obj_datasec(abfd)->vma, obj_datasec(abfd)->size,
07d6d2b8 1047 obj_datasec(abfd)->alignment_power,
eea6121a 1048 obj_bsssec(abfd)->vma, obj_bsssec(abfd)->size,
07d6d2b8 1049 obj_bsssec(abfd)->alignment_power);
e135f41b
NC
1050#endif
1051#endif
1052
1053 switch (adata(abfd).magic)
1054 {
1055 case o_magic:
1056 adjust_o_magic (abfd, execp);
1057 break;
1058 case z_magic:
1059 adjust_z_magic (abfd, execp);
1060 break;
1061 case n_magic:
1062 adjust_n_magic (abfd, execp);
1063 break;
1064 default:
1065 abort ();
1066 }
1067
1068#ifdef BFD_AOUT_DEBUG
1069 fprintf (stderr, " text=<%x,%x,%x> data=<%x,%x,%x> bss=<%x,%x>\n",
eea6121a 1070 obj_textsec(abfd)->vma, obj_textsec(abfd)->size,
07d6d2b8 1071 obj_textsec(abfd)->filepos,
eea6121a 1072 obj_datasec(abfd)->vma, obj_datasec(abfd)->size,
07d6d2b8 1073 obj_datasec(abfd)->filepos,
eea6121a 1074 obj_bsssec(abfd)->vma, obj_bsssec(abfd)->size);
e135f41b
NC
1075#endif
1076
b34976b6 1077 return TRUE;
e135f41b
NC
1078}
1079
116c20d2 1080/* Called by the BFD in response to a bfd_make_section request. */
e135f41b 1081
b34976b6 1082bfd_boolean
116c20d2 1083NAME (aout, new_section_hook) (bfd *abfd, asection *newsect)
e135f41b 1084{
116c20d2 1085 /* Align to double at least. */
e135f41b
NC
1086 newsect->alignment_power = bfd_get_arch_info(abfd)->section_align_power;
1087
e135f41b
NC
1088 if (bfd_get_format (abfd) == bfd_object)
1089 {
1090 if (obj_textsec (abfd) == NULL
f592407e 1091 && !strcmp (newsect->name, ".text"))
e135f41b
NC
1092 {
1093 obj_textsec(abfd)= newsect;
1094 newsect->target_index = N_TEXT;
e135f41b 1095 }
f592407e
AM
1096 else if (obj_datasec (abfd) == NULL
1097 && !strcmp (newsect->name, ".data"))
1098 {
1099 obj_datasec (abfd) = newsect;
1100 newsect->target_index = N_DATA;
1101 }
1102 else if (obj_bsssec (abfd) == NULL
1103 && !strcmp (newsect->name, ".bss"))
1104 {
1105 obj_bsssec (abfd) = newsect;
1106 newsect->target_index = N_BSS;
1107 }
1108 }
e135f41b 1109
116c20d2 1110 /* We allow more than three sections internally. */
f592407e 1111 return _bfd_generic_new_section_hook (abfd, newsect);
e135f41b
NC
1112}
1113
b34976b6 1114bfd_boolean
116c20d2
NC
1115NAME (aout, set_section_contents) (bfd *abfd,
1116 sec_ptr section,
1117 const void * location,
1118 file_ptr offset,
1119 bfd_size_type count)
e135f41b 1120{
e135f41b
NC
1121 if (! abfd->output_has_begun)
1122 {
3a8c4a5b 1123 if (! NAME (aout, adjust_sizes_and_vmas) (abfd))
b34976b6 1124 return FALSE;
e135f41b
NC
1125 }
1126
1127 if (section == obj_bsssec (abfd))
1128 {
1129 bfd_set_error (bfd_error_no_contents);
b34976b6 1130 return FALSE;
e135f41b
NC
1131 }
1132
1133 if (section != obj_textsec (abfd)
1134 && section != obj_datasec (abfd))
1135 {
4eca0228 1136 _bfd_error_handler
695344c0 1137 /* xgettext:c-format */
871b3ab2 1138 (_("%pB: can not represent section `%pA' in a.out object file format"),
dae82561 1139 abfd, section);
e135f41b 1140 bfd_set_error (bfd_error_nonrepresentable_section);
b34976b6 1141 return FALSE;
e135f41b
NC
1142 }
1143
1144 if (count != 0)
1145 {
1146 if (bfd_seek (abfd, section->filepos + offset, SEEK_SET) != 0
dc810e39 1147 || bfd_bwrite (location, count, abfd) != count)
b34976b6 1148 return FALSE;
3ad797fd
NC
1149
1150 /* If necessary, pad the section to its aligned size. */
1151 if ((section == obj_datasec (abfd)
1152 || section == obj_textsec (abfd))
1153 && count < section->size
1154 && (bfd_seek (abfd, section->filepos + offset + section->size - 1, SEEK_SET) != 0
1155 || bfd_bwrite ("", 1, abfd) != 1))
1156 return FALSE;
e135f41b
NC
1157 }
1158
b34976b6 1159 return TRUE;
e135f41b
NC
1160}
1161\f
1162/* Read the external symbols from an a.out file. */
1163
b34976b6 1164static bfd_boolean
116c20d2 1165aout_get_external_symbols (bfd *abfd)
e135f41b 1166{
116c20d2 1167 if (obj_aout_external_syms (abfd) == NULL)
e135f41b
NC
1168 {
1169 bfd_size_type count;
1170 struct external_nlist *syms;
1171
1172 count = exec_hdr (abfd)->a_syms / EXTERNAL_NLIST_SIZE;
1173
37e3922e
NC
1174 /* PR 17512: file: 011f5a08. */
1175 if (count == 0)
49987e5c
NC
1176 {
1177 obj_aout_external_syms (abfd) = NULL;
1178 obj_aout_external_sym_count (abfd) = count;
1179 return TRUE;
1180 }
1181
e135f41b 1182#ifdef USE_MMAP
82e51918
AM
1183 if (! bfd_get_file_window (abfd, obj_sym_filepos (abfd),
1184 exec_hdr (abfd)->a_syms,
b34976b6
AM
1185 &obj_aout_sym_window (abfd), TRUE))
1186 return FALSE;
e135f41b
NC
1187 syms = (struct external_nlist *) obj_aout_sym_window (abfd).data;
1188#else
1189 /* We allocate using malloc to make the values easy to free
1190 later on. If we put them on the objalloc it might not be
1191 possible to free them. */
116c20d2
NC
1192 syms = bfd_malloc (count * EXTERNAL_NLIST_SIZE);
1193 if (syms == NULL && count != 0)
b34976b6 1194 return FALSE;
e135f41b
NC
1195
1196 if (bfd_seek (abfd, obj_sym_filepos (abfd), SEEK_SET) != 0
dc810e39 1197 || (bfd_bread (syms, exec_hdr (abfd)->a_syms, abfd)
e135f41b
NC
1198 != exec_hdr (abfd)->a_syms))
1199 {
1200 free (syms);
b34976b6 1201 return FALSE;
e135f41b
NC
1202 }
1203#endif
1204
1205 obj_aout_external_syms (abfd) = syms;
1206 obj_aout_external_sym_count (abfd) = count;
1207 }
dc810e39 1208
e135f41b
NC
1209 if (obj_aout_external_strings (abfd) == NULL
1210 && exec_hdr (abfd)->a_syms != 0)
1211 {
1212 unsigned char string_chars[BYTES_IN_LONG];
1213 bfd_size_type stringsize;
1214 char *strings;
1215
1216 /* Get the size of the strings. */
1217 if (bfd_seek (abfd, obj_str_filepos (abfd), SEEK_SET) != 0
116c20d2 1218 || (bfd_bread ((void *) string_chars, (bfd_size_type) BYTES_IN_LONG,
dc810e39 1219 abfd) != BYTES_IN_LONG))
b34976b6 1220 return FALSE;
dc810e39 1221 stringsize = H_GET_32 (abfd, string_chars);
e135f41b
NC
1222
1223#ifdef USE_MMAP
82e51918 1224 if (! bfd_get_file_window (abfd, obj_str_filepos (abfd), stringsize,
b34976b6
AM
1225 &obj_aout_string_window (abfd), TRUE))
1226 return FALSE;
e135f41b
NC
1227 strings = (char *) obj_aout_string_window (abfd).data;
1228#else
116c20d2 1229 strings = bfd_malloc (stringsize + 1);
e135f41b 1230 if (strings == NULL)
b34976b6 1231 return FALSE;
e135f41b
NC
1232
1233 /* Skip space for the string count in the buffer for convenience
1234 when using indexes. */
dc810e39 1235 if (bfd_bread (strings + 4, stringsize - 4, abfd) != stringsize - 4)
e135f41b
NC
1236 {
1237 free (strings);
b34976b6 1238 return FALSE;
e135f41b
NC
1239 }
1240#endif
e135f41b
NC
1241 /* Ensure that a zero index yields an empty string. */
1242 strings[0] = '\0';
1243
1244 strings[stringsize - 1] = 0;
1245
1246 obj_aout_external_strings (abfd) = strings;
1247 obj_aout_external_string_size (abfd) = stringsize;
1248 }
1249
b34976b6 1250 return TRUE;
e135f41b
NC
1251}
1252
1253/* Translate an a.out symbol into a BFD symbol. The desc, other, type
1254 and symbol->value fields of CACHE_PTR will be set from the a.out
1255 nlist structure. This function is responsible for setting
1256 symbol->flags and symbol->section, and adjusting symbol->value. */
1257
b34976b6 1258static bfd_boolean
116c20d2
NC
1259translate_from_native_sym_flags (bfd *abfd,
1260 aout_symbol_type *cache_ptr)
e135f41b
NC
1261{
1262 flagword visible;
1263
1264 if (cache_ptr->type == N_FN)
1265 {
1266 asection *sec;
1267
1268 /* This is a debugging symbol. */
e135f41b
NC
1269 cache_ptr->symbol.flags = BSF_DEBUGGING;
1270
1271 /* Work out the symbol section. */
1272 switch (cache_ptr->type & N_TYPE)
1273 {
1274 case N_TEXT:
1275 case N_FN:
1276 sec = obj_textsec (abfd);
1277 break;
1278 case N_DATA:
1279 sec = obj_datasec (abfd);
1280 break;
1281 case N_BSS:
1282 sec = obj_bsssec (abfd);
1283 break;
1284 default:
1285 case N_ABS:
1286 sec = bfd_abs_section_ptr;
1287 break;
1288 }
1289
1290 cache_ptr->symbol.section = sec;
1291 cache_ptr->symbol.value -= sec->vma;
1292
b34976b6 1293 return TRUE;
e135f41b
NC
1294 }
1295
1296 /* Get the default visibility. This does not apply to all types, so
1297 we just hold it in a local variable to use if wanted. */
1298 if ((cache_ptr->type & N_EXT) == 0)
1299 visible = BSF_LOCAL;
1300 else
1301 visible = BSF_GLOBAL;
1302
1303 switch (cache_ptr->type)
1304 {
1305 default:
1306 case N_ABS: case N_ABS | N_EXT:
1307 cache_ptr->symbol.section = bfd_abs_section_ptr;
1308 cache_ptr->symbol.flags = visible;
1309 break;
1310
1311 case N_UNDF | N_EXT:
1312 if (cache_ptr->symbol.value != 0)
1313 {
1314 /* This is a common symbol. */
1315 cache_ptr->symbol.flags = BSF_GLOBAL;
1316 cache_ptr->symbol.section = bfd_com_section_ptr;
1317 }
1318 else
1319 {
1320 cache_ptr->symbol.flags = 0;
1321 cache_ptr->symbol.section = bfd_und_section_ptr;
1322 }
1323 break;
1324
1325 case N_TEXT: case N_TEXT | N_EXT:
1326 cache_ptr->symbol.section = obj_textsec (abfd);
1327 cache_ptr->symbol.value -= cache_ptr->symbol.section->vma;
1328 cache_ptr->symbol.flags = visible;
1329 break;
1330
1331 case N_DATA: case N_DATA | N_EXT:
1332 cache_ptr->symbol.section = obj_datasec (abfd);
1333 cache_ptr->symbol.value -= cache_ptr->symbol.section->vma;
1334 cache_ptr->symbol.flags = visible;
1335 break;
1336
1337 case N_BSS: case N_BSS | N_EXT:
1338 cache_ptr->symbol.section = obj_bsssec (abfd);
1339 cache_ptr->symbol.value -= cache_ptr->symbol.section->vma;
1340 cache_ptr->symbol.flags = visible;
1341 break;
1342 }
1343
b34976b6 1344 return TRUE;
e135f41b
NC
1345}
1346
1347/* Set the fields of SYM_POINTER according to CACHE_PTR. */
1348
b34976b6 1349static bfd_boolean
116c20d2
NC
1350translate_to_native_sym_flags (bfd *abfd,
1351 asymbol *cache_ptr,
1352 struct external_nlist *sym_pointer)
e135f41b
NC
1353{
1354 bfd_vma value = cache_ptr->value;
1355 asection *sec;
1356 bfd_vma off;
1357
1358 /* Mask out any existing type bits in case copying from one section
1359 to another. */
1360 sym_pointer->e_type[0] &= ~N_TYPE;
1361
1362 sec = bfd_get_section (cache_ptr);
1363 off = 0;
1364
1365 if (sec == NULL)
1366 {
1367 /* This case occurs, e.g., for the *DEBUG* section of a COFF
1368 file. */
4eca0228 1369 _bfd_error_handler
695344c0 1370 /* xgettext:c-format */
871b3ab2 1371 (_("%pB: can not represent section for symbol `%s' in a.out object file format"),
d003868e 1372 abfd, cache_ptr->name != NULL ? cache_ptr->name : "*unknown*");
e135f41b 1373 bfd_set_error (bfd_error_nonrepresentable_section);
b34976b6 1374 return FALSE;
e135f41b
NC
1375 }
1376
1377 if (sec->output_section != NULL)
1378 {
1379 off = sec->output_offset;
1380 sec = sec->output_section;
1381 }
1382
1383 if (bfd_is_abs_section (sec))
1384 sym_pointer->e_type[0] |= N_ABS;
1385 else if (sec == obj_textsec (abfd))
1386 sym_pointer->e_type[0] |= N_TEXT;
1387 else if (sec == obj_datasec (abfd))
1388 sym_pointer->e_type[0] |= N_DATA;
1389 else if (sec == obj_bsssec (abfd))
1390 sym_pointer->e_type[0] |= N_BSS;
1391 else if (bfd_is_und_section (sec))
1392 sym_pointer->e_type[0] = N_UNDF | N_EXT;
1393 else if (bfd_is_com_section (sec))
1394 sym_pointer->e_type[0] = N_UNDF | N_EXT;
1395 else
1396 {
4eca0228 1397 _bfd_error_handler
695344c0 1398 /* xgettext:c-format */
871b3ab2 1399 (_("%pB: can not represent section `%pA' in a.out object file format"),
d003868e 1400 abfd, sec);
e135f41b 1401 bfd_set_error (bfd_error_nonrepresentable_section);
b34976b6 1402 return FALSE;
e135f41b
NC
1403 }
1404
1405 /* Turn the symbol from section relative to absolute again */
1406 value += sec->vma + off;
1407
1408 if ((cache_ptr->flags & BSF_DEBUGGING) != 0)
1409 sym_pointer->e_type[0] = ((aout_symbol_type *) cache_ptr)->type;
1410 else if ((cache_ptr->flags & BSF_GLOBAL) != 0)
1411 sym_pointer->e_type[0] |= N_EXT;
1412
e135f41b
NC
1413 PUT_WORD(abfd, value, sym_pointer->e_value);
1414
b34976b6 1415 return TRUE;
e135f41b
NC
1416}
1417\f
1418/* Native-level interface to symbols. */
1419
1420asymbol *
116c20d2 1421NAME (aout, make_empty_symbol) (bfd *abfd)
e135f41b 1422{
dc810e39 1423 bfd_size_type amt = sizeof (aout_symbol_type);
d3ce72d0 1424 aout_symbol_type *new_symbol_type = bfd_zalloc (abfd, amt);
116c20d2 1425
d3ce72d0 1426 if (!new_symbol_type)
e135f41b 1427 return NULL;
d3ce72d0 1428 new_symbol_type->symbol.the_bfd = abfd;
e135f41b 1429
d3ce72d0 1430 return &new_symbol_type->symbol;
e135f41b
NC
1431}
1432
1433/* Translate a set of internal symbols into external symbols. */
1434
b34976b6 1435bfd_boolean
116c20d2
NC
1436NAME (aout, translate_symbol_table) (bfd *abfd,
1437 aout_symbol_type *in,
1438 struct external_nlist *ext,
1439 bfd_size_type count,
1440 char *str,
1441 bfd_size_type strsize,
1442 bfd_boolean dynamic)
e135f41b
NC
1443{
1444 struct external_nlist *ext_end;
1445
1446 ext_end = ext + count;
1447 for (; ext < ext_end; ext++, in++)
1448 {
1449 bfd_vma x;
1450
1451 x = GET_WORD (abfd, ext->e_strx);
1452 in->symbol.the_bfd = abfd;
1453
1454 /* For the normal symbols, the zero index points at the number
1455 of bytes in the string table but is to be interpreted as the
1456 null string. For the dynamic symbols, the number of bytes in
1457 the string table is stored in the __DYNAMIC structure and the
1458 zero index points at an actual string. */
1459 if (x == 0 && ! dynamic)
1460 in->symbol.name = "";
1461 else if (x < strsize)
1462 in->symbol.name = str + x;
1463 else
b34976b6 1464 return FALSE;
e135f41b
NC
1465
1466 in->symbol.value = GET_SWORD (abfd, ext->e_value);
116c20d2 1467 /* TODO: is 0 a safe value here? */
e135f41b
NC
1468 in->desc = 0;
1469 in->other = 0;
dc810e39 1470 in->type = H_GET_8 (abfd, ext->e_type);
e135f41b
NC
1471 in->symbol.udata.p = NULL;
1472
1473 if (! translate_from_native_sym_flags (abfd, in))
b34976b6 1474 return FALSE;
e135f41b
NC
1475
1476 if (dynamic)
1477 in->symbol.flags |= BSF_DYNAMIC;
1478 }
1479
b34976b6 1480 return TRUE;
e135f41b
NC
1481}
1482
1483/* We read the symbols into a buffer, which is discarded when this
1484 function exits. We read the strings into a buffer large enough to
116c20d2 1485 hold them all plus all the cached symbol entries. */
e135f41b 1486
b34976b6 1487bfd_boolean
116c20d2 1488NAME (aout, slurp_symbol_table) (bfd *abfd)
e135f41b
NC
1489{
1490 struct external_nlist *old_external_syms;
1491 aout_symbol_type *cached;
dc810e39 1492 bfd_size_type cached_size;
e135f41b 1493
116c20d2
NC
1494 /* If there's no work to be done, don't do any. */
1495 if (obj_aout_symbols (abfd) != NULL)
b34976b6 1496 return TRUE;
e135f41b
NC
1497
1498 old_external_syms = obj_aout_external_syms (abfd);
1499
1500 if (! aout_get_external_symbols (abfd))
b34976b6 1501 return FALSE;
e135f41b 1502
dc810e39
AM
1503 cached_size = obj_aout_external_sym_count (abfd);
1504 cached_size *= sizeof (aout_symbol_type);
116c20d2 1505 cached = bfd_zmalloc (cached_size);
e135f41b 1506 if (cached == NULL && cached_size != 0)
b34976b6 1507 return FALSE;
e135f41b
NC
1508
1509 /* Convert from external symbol information to internal. */
116c20d2 1510 if (! (NAME (aout, translate_symbol_table)
e135f41b
NC
1511 (abfd, cached,
1512 obj_aout_external_syms (abfd),
1513 obj_aout_external_sym_count (abfd),
1514 obj_aout_external_strings (abfd),
1515 obj_aout_external_string_size (abfd),
b34976b6 1516 FALSE)))
e135f41b
NC
1517 {
1518 free (cached);
b34976b6 1519 return FALSE;
e135f41b
NC
1520 }
1521
1522 bfd_get_symcount (abfd) = obj_aout_external_sym_count (abfd);
1523
1524 obj_aout_symbols (abfd) = cached;
1525
1526 /* It is very likely that anybody who calls this function will not
1527 want the external symbol information, so if it was allocated
1528 because of our call to aout_get_external_symbols, we free it up
1529 right away to save space. */
116c20d2
NC
1530 if (old_external_syms == NULL
1531 && obj_aout_external_syms (abfd) != NULL)
e135f41b
NC
1532 {
1533#ifdef USE_MMAP
1534 bfd_free_window (&obj_aout_sym_window (abfd));
1535#else
1536 free (obj_aout_external_syms (abfd));
1537#endif
1538 obj_aout_external_syms (abfd) = NULL;
1539 }
1540
b34976b6 1541 return TRUE;
e135f41b
NC
1542}
1543\f
1544/* We use a hash table when writing out symbols so that we only write
1545 out a particular string once. This helps particularly when the
1546 linker writes out stabs debugging entries, because each different
1547 contributing object file tends to have many duplicate stabs
1548 strings.
1549
1550 This hash table code breaks dbx on SunOS 4.1.3, so we don't do it
1551 if BFD_TRADITIONAL_FORMAT is set. */
1552
e135f41b
NC
1553/* Get the index of a string in a strtab, adding it if it is not
1554 already present. */
1555
1556static INLINE bfd_size_type
116c20d2
NC
1557add_to_stringtab (bfd *abfd,
1558 struct bfd_strtab_hash *tab,
1559 const char *str,
1560 bfd_boolean copy)
e135f41b 1561{
b34976b6 1562 bfd_boolean hash;
91d6fa6a 1563 bfd_size_type str_index;
e135f41b
NC
1564
1565 /* An index of 0 always means the empty string. */
1566 if (str == 0 || *str == '\0')
1567 return 0;
1568
1569 /* Don't hash if BFD_TRADITIONAL_FORMAT is set, because SunOS dbx
1570 doesn't understand a hashed string table. */
b34976b6 1571 hash = TRUE;
e135f41b 1572 if ((abfd->flags & BFD_TRADITIONAL_FORMAT) != 0)
b34976b6 1573 hash = FALSE;
e135f41b 1574
91d6fa6a 1575 str_index = _bfd_stringtab_add (tab, str, hash, copy);
e135f41b 1576
91d6fa6a 1577 if (str_index != (bfd_size_type) -1)
116c20d2
NC
1578 /* Add BYTES_IN_LONG to the return value to account for the
1579 space taken up by the string table size. */
91d6fa6a 1580 str_index += BYTES_IN_LONG;
e135f41b 1581
91d6fa6a 1582 return str_index;
e135f41b
NC
1583}
1584
1585/* Write out a strtab. ABFD is already at the right location in the
1586 file. */
1587
b34976b6 1588static bfd_boolean
116c20d2 1589emit_stringtab (bfd *abfd, struct bfd_strtab_hash *tab)
e135f41b
NC
1590{
1591 bfd_byte buffer[BYTES_IN_LONG];
1592
1593 /* The string table starts with the size. */
dc810e39 1594 H_PUT_32 (abfd, _bfd_stringtab_size (tab) + BYTES_IN_LONG, buffer);
116c20d2 1595 if (bfd_bwrite ((void *) buffer, (bfd_size_type) BYTES_IN_LONG, abfd)
dc810e39 1596 != BYTES_IN_LONG)
b34976b6 1597 return FALSE;
e135f41b
NC
1598
1599 return _bfd_stringtab_emit (abfd, tab);
1600}
1601\f
b34976b6 1602bfd_boolean
116c20d2 1603NAME (aout, write_syms) (bfd *abfd)
e135f41b
NC
1604{
1605 unsigned int count ;
1606 asymbol **generic = bfd_get_outsymbols (abfd);
1607 struct bfd_strtab_hash *strtab;
1608
1609 strtab = _bfd_stringtab_init ();
1610 if (strtab == NULL)
b34976b6 1611 return FALSE;
e135f41b
NC
1612
1613 for (count = 0; count < bfd_get_symcount (abfd); count++)
1614 {
1615 asymbol *g = generic[count];
1616 bfd_size_type indx;
1617 struct external_nlist nsp;
1618
dc810e39 1619 PUT_WORD (abfd, 0, nsp.e_unused);
e135f41b 1620
b34976b6 1621 indx = add_to_stringtab (abfd, strtab, g->name, FALSE);
e135f41b
NC
1622 if (indx == (bfd_size_type) -1)
1623 goto error_return;
dc810e39 1624 PUT_WORD (abfd, indx, nsp.e_strx);
e135f41b
NC
1625
1626 if (bfd_asymbol_flavour(g) == abfd->xvec->flavour)
dc810e39 1627 H_PUT_8 (abfd, aout_symbol(g)->type, nsp.e_type);
e135f41b 1628 else
dc810e39 1629 H_PUT_8 (abfd, 0, nsp.e_type);
e135f41b
NC
1630
1631 if (! translate_to_native_sym_flags (abfd, g, &nsp))
1632 goto error_return;
1633
dc810e39 1634 H_PUT_8 (abfd, 0, nsp.e_ovly);
e135f41b 1635
116c20d2 1636 if (bfd_bwrite ((void *)&nsp, (bfd_size_type) EXTERNAL_NLIST_SIZE, abfd)
e135f41b
NC
1637 != EXTERNAL_NLIST_SIZE)
1638 goto error_return;
1639
1640 /* NB: `KEEPIT' currently overlays `udata.p', so set this only
1641 here, at the end. */
1642 g->KEEPIT = count;
1643 }
1644
1645 if (! emit_stringtab (abfd, strtab))
1646 goto error_return;
1647
1648 _bfd_stringtab_free (strtab);
1649
b34976b6 1650 return TRUE;
e135f41b
NC
1651
1652error_return:
1653 _bfd_stringtab_free (strtab);
b34976b6 1654 return FALSE;
e135f41b
NC
1655}
1656
1657\f
1658long
116c20d2 1659NAME (aout, canonicalize_symtab) (bfd *abfd, asymbol **location)
e135f41b 1660{
116c20d2
NC
1661 unsigned int counter = 0;
1662 aout_symbol_type *symbase;
e135f41b 1663
116c20d2
NC
1664 if (!NAME (aout, slurp_symbol_table) (abfd))
1665 return -1;
e135f41b 1666
116c20d2
NC
1667 for (symbase = obj_aout_symbols (abfd); counter++ < bfd_get_symcount (abfd);)
1668 *(location++) = (asymbol *)(symbase++);
1669 *location++ =0;
1670 return bfd_get_symcount (abfd);
e135f41b
NC
1671}
1672
1673\f
116c20d2 1674/* Output extended relocation information to a file in target byte order. */
e135f41b 1675
116c20d2
NC
1676static void
1677pdp11_aout_swap_reloc_out (bfd *abfd, arelent *g, bfd_byte *natptr)
e135f41b
NC
1678{
1679 int r_index;
1680 int r_pcrel;
1681 int reloc_entry;
1682 int r_type;
1683 asymbol *sym = *(g->sym_ptr_ptr);
1684 asection *output_section = sym->section->output_section;
1685
1686 if (g->addend != 0)
1687 fprintf (stderr, "BFD: can't do this reloc addend stuff\n");
1688
1689 r_pcrel = g->howto->pc_relative;
1690
1691 if (bfd_is_abs_section (output_section))
1692 r_type = RABS;
1693 else if (output_section == obj_textsec (abfd))
1694 r_type = RTEXT;
1695 else if (output_section == obj_datasec (abfd))
1696 r_type = RDATA;
1697 else if (output_section == obj_bsssec (abfd))
1698 r_type = RBSS;
1699 else if (bfd_is_und_section (output_section))
1700 r_type = REXT;
1701 else if (bfd_is_com_section (output_section))
1702 r_type = REXT;
1703 else
1704 r_type = -1;
1705
1706 BFD_ASSERT (r_type != -1);
1707
1708 if (r_type == RABS)
1709 r_index = 0;
1710 else
1711 r_index = (*(g->sym_ptr_ptr))->KEEPIT;
1712
e135f41b
NC
1713 reloc_entry = r_index << 4 | r_type | r_pcrel;
1714
9dadfa79 1715 PUT_WORD (abfd, reloc_entry, natptr);
e135f41b
NC
1716}
1717
1718/* BFD deals internally with all things based from the section they're
1719 in. so, something in 10 bytes into a text section with a base of
1720 50 would have a symbol (.text+10) and know .text vma was 50.
1721
1722 Aout keeps all it's symbols based from zero, so the symbol would
1723 contain 60. This macro subs the base of each section from the value
1724 to give the true offset from the section */
1725
1726
07d6d2b8
AM
1727#define MOVE_ADDRESS(ad) \
1728 if (r_extern) \
e135f41b
NC
1729 { \
1730 /* Undefined symbol. */ \
1731 cache_ptr->sym_ptr_ptr = symbols + r_index; \
1732 cache_ptr->addend = ad; \
1733 } \
1734 else \
1735 { \
07d6d2b8 1736 /* Defined, section relative. replace symbol with pointer to \
e135f41b
NC
1737 symbol which points to section. */ \
1738 switch (r_index) \
1739 { \
1740 case N_TEXT: \
1741 case N_TEXT | N_EXT: \
1742 cache_ptr->sym_ptr_ptr = obj_textsec (abfd)->symbol_ptr_ptr; \
1743 cache_ptr->addend = ad - su->textsec->vma; \
1744 break; \
1745 case N_DATA: \
1746 case N_DATA | N_EXT: \
1747 cache_ptr->sym_ptr_ptr = obj_datasec (abfd)->symbol_ptr_ptr; \
1748 cache_ptr->addend = ad - su->datasec->vma; \
1749 break; \
1750 case N_BSS: \
1751 case N_BSS | N_EXT: \
1752 cache_ptr->sym_ptr_ptr = obj_bsssec (abfd)->symbol_ptr_ptr; \
1753 cache_ptr->addend = ad - su->bsssec->vma; \
1754 break; \
1755 default: \
1756 case N_ABS: \
1757 case N_ABS | N_EXT: \
1758 cache_ptr->sym_ptr_ptr = bfd_abs_section_ptr->symbol_ptr_ptr; \
1759 cache_ptr->addend = ad; \
1760 break; \
1761 } \
dc810e39 1762 }
e135f41b 1763
116c20d2 1764static void
07d6d2b8
AM
1765pdp11_aout_swap_reloc_in (bfd * abfd,
1766 bfd_byte * bytes,
1767 arelent * cache_ptr,
1768 bfd_size_type offset,
1769 asymbol ** symbols,
1770 bfd_size_type symcount)
e135f41b
NC
1771{
1772 struct aoutdata *su = &(abfd->tdata.aout_data->a);
1773 unsigned int r_index;
1774 int reloc_entry;
1775 int r_extern;
1776 int r_pcrel;
1777
116c20d2 1778 reloc_entry = GET_WORD (abfd, (void *) bytes);
e135f41b
NC
1779
1780 r_pcrel = reloc_entry & RELFLG;
1781
1782 cache_ptr->address = offset;
1783 cache_ptr->howto = howto_table_pdp11 + (r_pcrel ? 1 : 0);
1784
1785 if ((reloc_entry & RTYPE) == RABS)
1786 r_index = N_ABS;
1787 else
1788 r_index = RINDEX (reloc_entry);
1789
1790 /* r_extern reflects whether the symbol the reloc is against is
1791 local or global. */
1792 r_extern = (reloc_entry & RTYPE) == REXT;
1793
1794 if (r_extern && r_index > symcount)
1795 {
1796 /* We could arrange to return an error, but it might be useful
07d6d2b8 1797 to see the file even if it is bad. */
e135f41b
NC
1798 r_extern = 0;
1799 r_index = N_ABS;
1800 }
1801
1802 MOVE_ADDRESS(0);
1803}
1804
1805/* Read and swap the relocs for a section. */
1806
b34976b6 1807bfd_boolean
116c20d2 1808NAME (aout, slurp_reloc_table) (bfd *abfd, sec_ptr asect, asymbol **symbols)
e135f41b 1809{
9dadfa79 1810 bfd_byte *rptr;
dc810e39 1811 bfd_size_type count;
e135f41b 1812 bfd_size_type reloc_size;
116c20d2 1813 void * relocs;
e135f41b
NC
1814 arelent *reloc_cache;
1815 size_t each_size;
1816 unsigned int counter = 0;
1817 arelent *cache_ptr;
1818
1819 if (asect->relocation)
b34976b6 1820 return TRUE;
e135f41b
NC
1821
1822 if (asect->flags & SEC_CONSTRUCTOR)
b34976b6 1823 return TRUE;
e135f41b
NC
1824
1825 if (asect == obj_datasec (abfd))
1826 reloc_size = exec_hdr(abfd)->a_drsize;
1827 else if (asect == obj_textsec (abfd))
1828 reloc_size = exec_hdr(abfd)->a_trsize;
1829 else if (asect == obj_bsssec (abfd))
1830 reloc_size = 0;
1831 else
1832 {
1833 bfd_set_error (bfd_error_invalid_operation);
b34976b6 1834 return FALSE;
e135f41b
NC
1835 }
1836
1837 if (bfd_seek (abfd, asect->rel_filepos, SEEK_SET) != 0)
b34976b6 1838 return FALSE;
e135f41b
NC
1839
1840 each_size = obj_reloc_entry_size (abfd);
1841
dc810e39 1842 relocs = bfd_malloc (reloc_size);
e135f41b 1843 if (relocs == NULL && reloc_size != 0)
b34976b6 1844 return FALSE;
e135f41b 1845
dc810e39 1846 if (bfd_bread (relocs, reloc_size, abfd) != reloc_size)
e135f41b
NC
1847 {
1848 free (relocs);
b34976b6 1849 return FALSE;
e135f41b
NC
1850 }
1851
1852 count = reloc_size / each_size;
1853
116c20d2 1854 /* Count the number of NON-ZERO relocs, this is the count we want. */
e135f41b
NC
1855 {
1856 unsigned int real_count = 0;
1857
1858 for (counter = 0; counter < count; counter++)
1859 {
1860 int x;
1861
973ffd63 1862 x = GET_WORD (abfd, (char *) relocs + each_size * counter);
e135f41b
NC
1863 if (x != 0)
1864 real_count++;
1865 }
1866
1867 count = real_count;
1868 }
1869
116c20d2 1870 reloc_cache = bfd_zmalloc (count * sizeof (arelent));
e135f41b 1871 if (reloc_cache == NULL && count != 0)
b34976b6 1872 return FALSE;
e135f41b
NC
1873
1874 cache_ptr = reloc_cache;
1875
9dadfa79 1876 rptr = relocs;
e135f41b
NC
1877 for (counter = 0;
1878 counter < count;
9dadfa79 1879 counter++, rptr += RELOC_SIZE, cache_ptr++)
e135f41b 1880 {
116c20d2 1881 while (GET_WORD (abfd, (void *) rptr) == 0)
e135f41b 1882 {
9dadfa79 1883 rptr += RELOC_SIZE;
dc810e39 1884 if ((char *) rptr >= (char *) relocs + reloc_size)
e135f41b
NC
1885 goto done;
1886 }
1887
1888 pdp11_aout_swap_reloc_in (abfd, rptr, cache_ptr,
dc810e39
AM
1889 (bfd_size_type) ((char *) rptr - (char *) relocs),
1890 symbols,
1891 (bfd_size_type) bfd_get_symcount (abfd));
e135f41b
NC
1892 }
1893 done:
1894 /* Just in case, if rptr >= relocs + reloc_size should happen
116c20d2 1895 too early. */
e135f41b
NC
1896 BFD_ASSERT (counter == count);
1897
1898 free (relocs);
1899
1900 asect->relocation = reloc_cache;
1901 asect->reloc_count = cache_ptr - reloc_cache;
1902
b34976b6 1903 return TRUE;
e135f41b
NC
1904}
1905
1906/* Write out a relocation section into an object file. */
1907
b34976b6 1908bfd_boolean
116c20d2 1909NAME (aout, squirt_out_relocs) (bfd *abfd, asection *section)
e135f41b
NC
1910{
1911 arelent **generic;
1912 unsigned char *native;
1913 unsigned int count = section->reloc_count;
dc810e39 1914 bfd_size_type natsize;
e135f41b 1915
eea6121a 1916 natsize = section->size;
116c20d2 1917 native = bfd_zalloc (abfd, natsize);
e135f41b 1918 if (!native)
b34976b6 1919 return FALSE;
e135f41b 1920
e135f41b
NC
1921 generic = section->orelocation;
1922 if (generic != NULL)
1923 {
1924 while (count > 0)
1925 {
9dadfa79 1926 bfd_byte *r;
e135f41b 1927
9dadfa79 1928 r = native + (*generic)->address;
e135f41b
NC
1929 pdp11_aout_swap_reloc_out (abfd, *generic, r);
1930 count--;
1931 generic++;
1932 }
1933 }
1934
116c20d2 1935 if (bfd_bwrite ((void *) native, natsize, abfd) != natsize)
e135f41b 1936 {
dc810e39 1937 bfd_release (abfd, native);
b34976b6 1938 return FALSE;
e135f41b
NC
1939 }
1940
1941 bfd_release (abfd, native);
b34976b6 1942 return TRUE;
e135f41b
NC
1943}
1944
116c20d2
NC
1945/* This is stupid. This function should be a boolean predicate. */
1946
e135f41b 1947long
116c20d2
NC
1948NAME (aout, canonicalize_reloc) (bfd *abfd,
1949 sec_ptr section,
1950 arelent **relptr,
1951 asymbol **symbols)
e135f41b
NC
1952{
1953 arelent *tblptr = section->relocation;
1954 unsigned int count;
1955
1956 if (section == obj_bsssec (abfd))
1957 {
1958 *relptr = NULL;
1959 return 0;
1960 }
1961
116c20d2 1962 if (!(tblptr || NAME (aout, slurp_reloc_table)(abfd, section, symbols)))
e135f41b
NC
1963 return -1;
1964
1965 if (section->flags & SEC_CONSTRUCTOR)
1966 {
1967 arelent_chain *chain = section->constructor_chain;
1968
1969 for (count = 0; count < section->reloc_count; count ++)
1970 {
1971 *relptr ++ = &chain->relent;
1972 chain = chain->next;
1973 }
1974 }
1975 else
1976 {
1977 tblptr = section->relocation;
1978
1979 for (count = 0; count++ < section->reloc_count;)
1980 *relptr++ = tblptr++;
1981 }
1982
1983 *relptr = 0;
1984
1985 return section->reloc_count;
1986}
1987
1988long
116c20d2 1989NAME (aout, get_reloc_upper_bound) (bfd *abfd, sec_ptr asect)
e135f41b
NC
1990{
1991 if (bfd_get_format (abfd) != bfd_object)
1992 {
1993 bfd_set_error (bfd_error_invalid_operation);
1994 return -1;
1995 }
1996
dc810e39 1997 if (asect->flags & SEC_CONSTRUCTOR)
116c20d2 1998 return (sizeof (arelent *) * (asect->reloc_count + 1));
e135f41b
NC
1999
2000 if (asect == obj_datasec (abfd))
2001 return (sizeof (arelent *)
116c20d2 2002 * ((exec_hdr (abfd)->a_drsize / obj_reloc_entry_size (abfd))
e135f41b
NC
2003 + 1));
2004
2005 if (asect == obj_textsec (abfd))
2006 return (sizeof (arelent *)
116c20d2 2007 * ((exec_hdr (abfd)->a_trsize / obj_reloc_entry_size (abfd))
e135f41b
NC
2008 + 1));
2009
2010 /* TODO: why are there two if statements for obj_bsssec()? */
2011
2012 if (asect == obj_bsssec (abfd))
2013 return sizeof (arelent *);
2014
2015 if (asect == obj_bsssec (abfd))
2016 return 0;
2017
2018 bfd_set_error (bfd_error_invalid_operation);
2019 return -1;
2020}
2021
2022\f
2023long
116c20d2 2024NAME (aout, get_symtab_upper_bound) (bfd *abfd)
e135f41b 2025{
116c20d2 2026 if (!NAME (aout, slurp_symbol_table) (abfd))
e135f41b
NC
2027 return -1;
2028
2029 return (bfd_get_symcount (abfd) + 1) * (sizeof (aout_symbol_type *));
2030}
2031
2032alent *
116c20d2
NC
2033NAME (aout, get_lineno) (bfd * abfd ATTRIBUTE_UNUSED,
2034 asymbol * symbol ATTRIBUTE_UNUSED)
e135f41b 2035{
116c20d2 2036 return NULL;
e135f41b
NC
2037}
2038
2039void
116c20d2
NC
2040NAME (aout, get_symbol_info) (bfd * abfd ATTRIBUTE_UNUSED,
2041 asymbol *symbol,
2042 symbol_info *ret)
e135f41b
NC
2043{
2044 bfd_symbol_info (symbol, ret);
2045
2046 if (ret->type == '?')
2047 {
2048 int type_code = aout_symbol(symbol)->type & 0xff;
2049 const char *stab_name = bfd_get_stab_name (type_code);
2050 static char buf[10];
2051
2052 if (stab_name == NULL)
2053 {
2054 sprintf(buf, "(%d)", type_code);
2055 stab_name = buf;
2056 }
2057 ret->type = '-';
116c20d2
NC
2058 ret->stab_type = type_code;
2059 ret->stab_other = (unsigned) (aout_symbol(symbol)->other & 0xff);
2060 ret->stab_desc = (unsigned) (aout_symbol(symbol)->desc & 0xffff);
2061 ret->stab_name = stab_name;
e135f41b
NC
2062 }
2063}
2064
e135f41b 2065void
116c20d2
NC
2066NAME (aout, print_symbol) (bfd * abfd,
2067 void * afile,
2068 asymbol *symbol,
2069 bfd_print_symbol_type how)
e135f41b 2070{
116c20d2 2071 FILE *file = (FILE *) afile;
e135f41b
NC
2072
2073 switch (how)
2074 {
2075 case bfd_print_symbol_name:
2076 if (symbol->name)
2077 fprintf(file,"%s", symbol->name);
2078 break;
2079 case bfd_print_symbol_more:
116c20d2
NC
2080 fprintf(file,"%4x %2x %2x",
2081 (unsigned) (aout_symbol (symbol)->desc & 0xffff),
2082 (unsigned) (aout_symbol (symbol)->other & 0xff),
2083 (unsigned) (aout_symbol (symbol)->type));
e135f41b
NC
2084 break;
2085 case bfd_print_symbol_all:
2086 {
dc810e39 2087 const char *section_name = symbol->section->name;
e135f41b 2088
116c20d2 2089 bfd_print_symbol_vandf (abfd, (void *) file, symbol);
e135f41b
NC
2090
2091 fprintf (file," %-5s %04x %02x %02x",
2092 section_name,
116c20d2
NC
2093 (unsigned) (aout_symbol (symbol)->desc & 0xffff),
2094 (unsigned) (aout_symbol (symbol)->other & 0xff),
2095 (unsigned) (aout_symbol (symbol)->type & 0xff));
e135f41b
NC
2096 if (symbol->name)
2097 fprintf(file," %s", symbol->name);
2098 }
2099 break;
2100 }
2101}
2102
2103/* If we don't have to allocate more than 1MB to hold the generic
2104 symbols, we use the generic minisymbol method: it's faster, since
2105 it only translates the symbols once, not multiple times. */
2106#define MINISYM_THRESHOLD (1000000 / sizeof (asymbol))
2107
2108/* Read minisymbols. For minisymbols, we use the unmodified a.out
2109 symbols. The minisymbol_to_symbol function translates these into
2110 BFD asymbol structures. */
2111
2112long
116c20d2
NC
2113NAME (aout, read_minisymbols) (bfd *abfd,
2114 bfd_boolean dynamic,
2115 void * *minisymsp,
2116 unsigned int *sizep)
e135f41b
NC
2117{
2118 if (dynamic)
116c20d2
NC
2119 /* We could handle the dynamic symbols here as well, but it's
2120 easier to hand them off. */
2121 return _bfd_generic_read_minisymbols (abfd, dynamic, minisymsp, sizep);
e135f41b
NC
2122
2123 if (! aout_get_external_symbols (abfd))
2124 return -1;
2125
2126 if (obj_aout_external_sym_count (abfd) < MINISYM_THRESHOLD)
2127 return _bfd_generic_read_minisymbols (abfd, dynamic, minisymsp, sizep);
2128
116c20d2 2129 *minisymsp = (void *) obj_aout_external_syms (abfd);
e135f41b
NC
2130
2131 /* By passing the external symbols back from this routine, we are
2132 giving up control over the memory block. Clear
2133 obj_aout_external_syms, so that we do not try to free it
2134 ourselves. */
2135 obj_aout_external_syms (abfd) = NULL;
2136
2137 *sizep = EXTERNAL_NLIST_SIZE;
2138 return obj_aout_external_sym_count (abfd);
2139}
2140
2141/* Convert a minisymbol to a BFD asymbol. A minisymbol is just an
2142 unmodified a.out symbol. The SYM argument is a structure returned
2143 by bfd_make_empty_symbol, which we fill in here. */
2144
2145asymbol *
116c20d2
NC
2146NAME (aout, minisymbol_to_symbol) (bfd *abfd,
2147 bfd_boolean dynamic,
2148 const void * minisym,
2149 asymbol *sym)
e135f41b
NC
2150{
2151 if (dynamic
2152 || obj_aout_external_sym_count (abfd) < MINISYM_THRESHOLD)
2153 return _bfd_generic_minisymbol_to_symbol (abfd, dynamic, minisym, sym);
2154
2155 memset (sym, 0, sizeof (aout_symbol_type));
2156
2157 /* We call translate_symbol_table to translate a single symbol. */
116c20d2 2158 if (! (NAME (aout, translate_symbol_table)
e135f41b
NC
2159 (abfd,
2160 (aout_symbol_type *) sym,
2161 (struct external_nlist *) minisym,
2162 (bfd_size_type) 1,
2163 obj_aout_external_strings (abfd),
2164 obj_aout_external_string_size (abfd),
b34976b6 2165 FALSE)))
e135f41b
NC
2166 return NULL;
2167
2168 return sym;
2169}
2170
116c20d2
NC
2171/* Provided a BFD, a section and an offset into the section, calculate
2172 and return the name of the source file and the line nearest to the
2173 wanted location. */
e135f41b 2174
b34976b6 2175bfd_boolean
116c20d2 2176NAME (aout, find_nearest_line) (bfd *abfd,
116c20d2 2177 asymbol **symbols,
fb167eb2 2178 asection *section,
116c20d2
NC
2179 bfd_vma offset,
2180 const char **filename_ptr,
2181 const char **functionname_ptr,
fb167eb2
AM
2182 unsigned int *line_ptr,
2183 unsigned int *discriminator_ptr)
e135f41b 2184{
116c20d2 2185 /* Run down the file looking for the filename, function and linenumber. */
e135f41b 2186 asymbol **p;
dc810e39
AM
2187 const char *directory_name = NULL;
2188 const char *main_file_name = NULL;
2189 const char *current_file_name = NULL;
116c20d2 2190 const char *line_file_name = NULL; /* Value of current_file_name at line number. */
e135f41b
NC
2191 bfd_vma low_line_vma = 0;
2192 bfd_vma low_func_vma = 0;
2193 asymbol *func = 0;
2194 size_t filelen, funclen;
2195 char *buf;
2196
2197 *filename_ptr = abfd->filename;
2198 *functionname_ptr = 0;
2199 *line_ptr = 0;
fb167eb2
AM
2200 if (discriminator_ptr)
2201 *discriminator_ptr = 0;
e135f41b 2202
116c20d2 2203 if (symbols != NULL)
e135f41b
NC
2204 {
2205 for (p = symbols; *p; p++)
2206 {
2207 aout_symbol_type *q = (aout_symbol_type *)(*p);
2208 next:
2209 switch (q->type)
2210 {
2211 case N_TEXT:
2212 /* If this looks like a file name symbol, and it comes after
2213 the line number we have found so far, but before the
2214 offset, then we have probably not found the right line
2215 number. */
2216 if (q->symbol.value <= offset
2217 && ((q->symbol.value > low_line_vma
2218 && (line_file_name != NULL
2219 || *line_ptr != 0))
2220 || (q->symbol.value > low_func_vma
2221 && func != NULL)))
2222 {
2223 const char * symname;
2224
2225 symname = q->symbol.name;
2226 if (strcmp (symname + strlen (symname) - 2, ".o") == 0)
2227 {
2228 if (q->symbol.value > low_line_vma)
2229 {
2230 *line_ptr = 0;
2231 line_file_name = NULL;
2232 }
2233 if (q->symbol.value > low_func_vma)
2234 func = NULL;
2235 }
2236 }
2237 break;
2238
2239 case N_SO:
2240 /* If this symbol is less than the offset, but greater than
2241 the line number we have found so far, then we have not
2242 found the right line number. */
2243 if (q->symbol.value <= offset)
2244 {
2245 if (q->symbol.value > low_line_vma)
2246 {
2247 *line_ptr = 0;
2248 line_file_name = NULL;
2249 }
2250 if (q->symbol.value > low_func_vma)
2251 func = NULL;
2252 }
2253
2254 main_file_name = current_file_name = q->symbol.name;
116c20d2 2255 /* Look ahead to next symbol to check if that too is an N_SO. */
e135f41b
NC
2256 p++;
2257 if (*p == NULL)
2258 break;
2259 q = (aout_symbol_type *)(*p);
116c20d2 2260 if (q->type != (int) N_SO)
e135f41b
NC
2261 goto next;
2262
116c20d2 2263 /* Found a second N_SO First is directory; second is filename. */
e135f41b
NC
2264 directory_name = current_file_name;
2265 main_file_name = current_file_name = q->symbol.name;
2266 if (obj_textsec(abfd) != section)
2267 goto done;
2268 break;
2269 case N_SOL:
2270 current_file_name = q->symbol.name;
2271 break;
2272
2273 case N_SLINE:
2274 case N_DSLINE:
2275 case N_BSLINE:
2276 /* We'll keep this if it resolves nearer than the one we have
2277 already. */
2278 if (q->symbol.value >= low_line_vma
2279 && q->symbol.value <= offset)
2280 {
2281 *line_ptr = q->desc;
2282 low_line_vma = q->symbol.value;
2283 line_file_name = current_file_name;
2284 }
2285 break;
2286
2287 case N_FUN:
2288 {
116c20d2 2289 /* We'll keep this if it is nearer than the one we have already. */
e135f41b
NC
2290 if (q->symbol.value >= low_func_vma &&
2291 q->symbol.value <= offset)
2292 {
2293 low_func_vma = q->symbol.value;
116c20d2 2294 func = (asymbol *) q;
e135f41b
NC
2295 }
2296 else if (q->symbol.value > offset)
2297 goto done;
2298 }
2299 break;
2300 }
2301 }
2302 }
2303
2304 done:
2305 if (*line_ptr != 0)
2306 main_file_name = line_file_name;
2307
2308 if (main_file_name == NULL
2309 || main_file_name[0] == '/'
2310 || directory_name == NULL)
2311 filelen = 0;
2312 else
2313 filelen = strlen (directory_name) + strlen (main_file_name);
2314 if (func == NULL)
2315 funclen = 0;
2316 else
2317 funclen = strlen (bfd_asymbol_name (func));
2318
2319 if (adata (abfd).line_buf != NULL)
2320 free (adata (abfd).line_buf);
2321 if (filelen + funclen == 0)
2322 adata (abfd).line_buf = buf = NULL;
2323 else
2324 {
116c20d2 2325 buf = bfd_malloc ((bfd_size_type) filelen + funclen + 3);
e135f41b
NC
2326 adata (abfd).line_buf = buf;
2327 if (buf == NULL)
b34976b6 2328 return FALSE;
e135f41b
NC
2329 }
2330
2331 if (main_file_name != NULL)
2332 {
2333 if (main_file_name[0] == '/' || directory_name == NULL)
2334 *filename_ptr = main_file_name;
2335 else
2336 {
2337 sprintf (buf, "%s%s", directory_name, main_file_name);
2338 *filename_ptr = buf;
2339 buf += filelen + 1;
2340 }
2341 }
2342
2343 if (func)
2344 {
2345 const char *function = func->name;
dc810e39 2346 char *colon;
e135f41b
NC
2347
2348 /* The caller expects a symbol name. We actually have a
2349 function name, without the leading underscore. Put the
2350 underscore back in, so that the caller gets a symbol name. */
2351 if (bfd_get_symbol_leading_char (abfd) == '\0')
2352 strcpy (buf, function);
2353 else
2354 {
2355 buf[0] = bfd_get_symbol_leading_char (abfd);
2356 strcpy (buf + 1, function);
2357 }
2358
2359 /* Have to remove : stuff. */
dc810e39
AM
2360 colon = strchr (buf, ':');
2361 if (colon != NULL)
2362 *colon = '\0';
e135f41b
NC
2363 *functionname_ptr = buf;
2364 }
2365
b34976b6 2366 return TRUE;
e135f41b
NC
2367}
2368
2369int
a6b96beb
AM
2370NAME (aout, sizeof_headers) (bfd *abfd,
2371 struct bfd_link_info *info ATTRIBUTE_UNUSED)
e135f41b 2372{
116c20d2 2373 return adata (abfd).exec_bytes_size;
e135f41b
NC
2374}
2375
2376/* Free all information we have cached for this BFD. We can always
2377 read it again later if we need it. */
2378
b34976b6 2379bfd_boolean
116c20d2 2380NAME (aout, bfd_free_cached_info) (bfd *abfd)
e135f41b
NC
2381{
2382 asection *o;
2383
2384 if (bfd_get_format (abfd) != bfd_object)
b34976b6 2385 return TRUE;
e135f41b
NC
2386
2387#define BFCI_FREE(x) if (x != NULL) { free (x); x = NULL; }
2388 BFCI_FREE (obj_aout_symbols (abfd));
116c20d2 2389
e135f41b
NC
2390#ifdef USE_MMAP
2391 obj_aout_external_syms (abfd) = 0;
2392 bfd_free_window (&obj_aout_sym_window (abfd));
2393 bfd_free_window (&obj_aout_string_window (abfd));
2394 obj_aout_external_strings (abfd) = 0;
2395#else
2396 BFCI_FREE (obj_aout_external_syms (abfd));
2397 BFCI_FREE (obj_aout_external_strings (abfd));
2398#endif
116c20d2 2399 for (o = abfd->sections; o != NULL; o = o->next)
e135f41b
NC
2400 BFCI_FREE (o->relocation);
2401#undef BFCI_FREE
2402
b34976b6 2403 return TRUE;
e135f41b
NC
2404}
2405\f
e135f41b
NC
2406/* Routine to create an entry in an a.out link hash table. */
2407
2408struct bfd_hash_entry *
116c20d2
NC
2409NAME (aout, link_hash_newfunc) (struct bfd_hash_entry *entry,
2410 struct bfd_hash_table *table,
2411 const char *string)
e135f41b
NC
2412{
2413 struct aout_link_hash_entry *ret = (struct aout_link_hash_entry *) entry;
2414
2415 /* Allocate the structure if it has not already been allocated by a
2416 subclass. */
116c20d2
NC
2417 if (ret == NULL)
2418 ret = bfd_hash_allocate (table, sizeof (* ret));
2419 if (ret == NULL)
2420 return NULL;
e135f41b
NC
2421
2422 /* Call the allocation method of the superclass. */
116c20d2
NC
2423 ret = (struct aout_link_hash_entry *)
2424 _bfd_link_hash_newfunc ((struct bfd_hash_entry *) ret, table, string);
e135f41b
NC
2425 if (ret)
2426 {
2427 /* Set local fields. */
b34976b6 2428 ret->written = FALSE;
e135f41b
NC
2429 ret->indx = -1;
2430 }
2431
2432 return (struct bfd_hash_entry *) ret;
2433}
2434
2435/* Initialize an a.out link hash table. */
2436
b34976b6 2437bfd_boolean
116c20d2
NC
2438NAME (aout, link_hash_table_init) (struct aout_link_hash_table *table,
2439 bfd *abfd,
2440 struct bfd_hash_entry *(*newfunc) (struct bfd_hash_entry *,
2441 struct bfd_hash_table *,
66eb6687
AM
2442 const char *),
2443 unsigned int entsize)
e135f41b 2444{
66eb6687 2445 return _bfd_link_hash_table_init (&table->root, abfd, newfunc, entsize);
e135f41b
NC
2446}
2447
2448/* Create an a.out link hash table. */
2449
2450struct bfd_link_hash_table *
116c20d2 2451NAME (aout, link_hash_table_create) (bfd *abfd)
e135f41b
NC
2452{
2453 struct aout_link_hash_table *ret;
dc810e39 2454 bfd_size_type amt = sizeof (struct aout_link_hash_table);
e135f41b 2455
22cdc249 2456 ret = bfd_malloc (amt);
e135f41b 2457 if (ret == NULL)
116c20d2
NC
2458 return NULL;
2459 if (! NAME (aout, link_hash_table_init) (ret, abfd,
66eb6687
AM
2460 NAME (aout, link_hash_newfunc),
2461 sizeof (struct aout_link_hash_entry)))
e135f41b
NC
2462 {
2463 free (ret);
116c20d2 2464 return NULL;
e135f41b
NC
2465 }
2466 return &ret->root;
2467}
2468
116c20d2
NC
2469/* Free up the internal symbols read from an a.out file. */
2470
2471static bfd_boolean
2472aout_link_free_symbols (bfd *abfd)
2473{
2474 if (obj_aout_external_syms (abfd) != NULL)
2475 {
2476#ifdef USE_MMAP
2477 bfd_free_window (&obj_aout_sym_window (abfd));
2478#else
2479 free ((void *) obj_aout_external_syms (abfd));
2480#endif
2481 obj_aout_external_syms (abfd) = NULL;
2482 }
2483
2484 if (obj_aout_external_strings (abfd) != NULL)
2485 {
2486#ifdef USE_MMAP
2487 bfd_free_window (&obj_aout_string_window (abfd));
2488#else
2489 free ((void *) obj_aout_external_strings (abfd));
2490#endif
2491 obj_aout_external_strings (abfd) = NULL;
2492 }
2493 return TRUE;
2494}
2495
e135f41b
NC
2496/* Given an a.out BFD, add symbols to the global hash table as
2497 appropriate. */
2498
b34976b6 2499bfd_boolean
116c20d2 2500NAME (aout, link_add_symbols) (bfd *abfd, struct bfd_link_info *info)
e135f41b
NC
2501{
2502 switch (bfd_get_format (abfd))
2503 {
2504 case bfd_object:
2505 return aout_link_add_object_symbols (abfd, info);
2506 case bfd_archive:
2507 return _bfd_generic_link_add_archive_symbols
2508 (abfd, info, aout_link_check_archive_element);
2509 default:
2510 bfd_set_error (bfd_error_wrong_format);
b34976b6 2511 return FALSE;
e135f41b
NC
2512 }
2513}
2514
2515/* Add symbols from an a.out object file. */
2516
b34976b6 2517static bfd_boolean
116c20d2 2518aout_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info)
e135f41b
NC
2519{
2520 if (! aout_get_external_symbols (abfd))
b34976b6 2521 return FALSE;
e135f41b 2522 if (! aout_link_add_symbols (abfd, info))
b34976b6 2523 return FALSE;
e135f41b
NC
2524 if (! info->keep_memory)
2525 {
2526 if (! aout_link_free_symbols (abfd))
b34976b6 2527 return FALSE;
e135f41b 2528 }
b34976b6 2529 return TRUE;
e135f41b
NC
2530}
2531
e135f41b
NC
2532/* Look through the internal symbols to see if this object file should
2533 be included in the link. We should include this object file if it
2534 defines any symbols which are currently undefined. If this object
2535 file defines a common symbol, then we may adjust the size of the
2536 known symbol but we do not include the object file in the link
2537 (unless there is some other reason to include it). */
2538
b34976b6 2539static bfd_boolean
116c20d2
NC
2540aout_link_check_ar_symbols (bfd *abfd,
2541 struct bfd_link_info *info,
5d3236ee
DK
2542 bfd_boolean *pneeded,
2543 bfd **subsbfd)
e135f41b 2544{
116c20d2 2545 struct external_nlist *p;
e135f41b
NC
2546 struct external_nlist *pend;
2547 char *strings;
2548
b34976b6 2549 *pneeded = FALSE;
e135f41b
NC
2550
2551 /* Look through all the symbols. */
2552 p = obj_aout_external_syms (abfd);
2553 pend = p + obj_aout_external_sym_count (abfd);
2554 strings = obj_aout_external_strings (abfd);
2555 for (; p < pend; p++)
2556 {
dc810e39 2557 int type = H_GET_8 (abfd, p->e_type);
e135f41b
NC
2558 const char *name;
2559 struct bfd_link_hash_entry *h;
2560
2561 /* Ignore symbols that are not externally visible. This is an
2562 optimization only, as we check the type more thoroughly
2563 below. */
2564 if ((type & N_EXT) == 0
2565 || type == N_FN)
2566 continue;
2567
2568 name = strings + GET_WORD (abfd, p->e_strx);
b34976b6 2569 h = bfd_link_hash_lookup (info->hash, name, FALSE, FALSE, TRUE);
e135f41b
NC
2570
2571 /* We are only interested in symbols that are currently
2572 undefined or common. */
116c20d2 2573 if (h == NULL
e135f41b
NC
2574 || (h->type != bfd_link_hash_undefined
2575 && h->type != bfd_link_hash_common))
2576 continue;
2577
2578 if (type == (N_TEXT | N_EXT)
2579 || type == (N_DATA | N_EXT)
2580 || type == (N_BSS | N_EXT)
2581 || type == (N_ABS | N_EXT))
2582 {
2583 /* This object file defines this symbol. We must link it
2584 in. This is true regardless of whether the current
2585 definition of the symbol is undefined or common. If the
2586 current definition is common, we have a case in which we
2587 have already seen an object file including
07d6d2b8 2588 int a;
e135f41b 2589 and this object file from the archive includes
07d6d2b8 2590 int a = 5;
e135f41b
NC
2591 In such a case we must include this object file.
2592
2593 FIXME: The SunOS 4.1.3 linker will pull in the archive
2594 element if the symbol is defined in the .data section,
2595 but not if it is defined in the .text section. That
2596 seems a bit crazy to me, and I haven't implemented it.
2597 However, it might be correct. */
0e144ba7
AM
2598 if (!(*info->callbacks
2599 ->add_archive_element) (info, abfd, name, subsbfd))
b95a0a31 2600 continue;
b34976b6
AM
2601 *pneeded = TRUE;
2602 return TRUE;
e135f41b
NC
2603 }
2604
2605 if (type == (N_UNDF | N_EXT))
2606 {
2607 bfd_vma value;
2608
2609 value = GET_WORD (abfd, p->e_value);
2610 if (value != 0)
2611 {
2612 /* This symbol is common in the object from the archive
2613 file. */
2614 if (h->type == bfd_link_hash_undefined)
2615 {
2616 bfd *symbfd;
2617 unsigned int power;
2618
2619 symbfd = h->u.undef.abfd;
116c20d2 2620 if (symbfd == NULL)
e135f41b
NC
2621 {
2622 /* This symbol was created as undefined from
2623 outside BFD. We assume that we should link
2624 in the object file. This is done for the -u
2625 option in the linker. */
0e144ba7
AM
2626 if (!(*info->callbacks
2627 ->add_archive_element) (info, abfd, name, subsbfd))
b34976b6
AM
2628 return FALSE;
2629 *pneeded = TRUE;
2630 return TRUE;
e135f41b
NC
2631 }
2632 /* Turn the current link symbol into a common
2633 symbol. It is already on the undefs list. */
2634 h->type = bfd_link_hash_common;
116c20d2
NC
2635 h->u.c.p = bfd_hash_allocate (&info->hash->table,
2636 sizeof (struct bfd_link_hash_common_entry));
e135f41b 2637 if (h->u.c.p == NULL)
b34976b6 2638 return FALSE;
e135f41b
NC
2639
2640 h->u.c.size = value;
2641
2642 /* FIXME: This isn't quite right. The maximum
2643 alignment of a common symbol should be set by the
2644 architecture of the output file, not of the input
2645 file. */
2646 power = bfd_log2 (value);
2647 if (power > bfd_get_arch_info (abfd)->section_align_power)
2648 power = bfd_get_arch_info (abfd)->section_align_power;
2649 h->u.c.p->alignment_power = power;
2650
2651 h->u.c.p->section = bfd_make_section_old_way (symbfd,
2652 "COMMON");
2653 }
2654 else
2655 {
2656 /* Adjust the size of the common symbol if
2657 necessary. */
2658 if (value > h->u.c.size)
2659 h->u.c.size = value;
2660 }
2661 }
2662 }
2663 }
2664
2665 /* We do not need this object file. */
b34976b6 2666 return TRUE;
e135f41b
NC
2667}
2668
116c20d2
NC
2669/* Check a single archive element to see if we need to include it in
2670 the link. *PNEEDED is set according to whether this element is
2671 needed in the link or not. This is called from
2672 _bfd_generic_link_add_archive_symbols. */
2673
2674static bfd_boolean
2675aout_link_check_archive_element (bfd *abfd,
2676 struct bfd_link_info *info,
13e570f8
AM
2677 struct bfd_link_hash_entry *h ATTRIBUTE_UNUSED,
2678 const char *name ATTRIBUTE_UNUSED,
116c20d2
NC
2679 bfd_boolean *pneeded)
2680{
0e144ba7
AM
2681 bfd *oldbfd;
2682 bfd_boolean needed;
5d3236ee 2683
0e144ba7 2684 if (!aout_get_external_symbols (abfd))
116c20d2
NC
2685 return FALSE;
2686
0e144ba7
AM
2687 oldbfd = abfd;
2688 if (!aout_link_check_ar_symbols (abfd, info, pneeded, &abfd))
116c20d2
NC
2689 return FALSE;
2690
0e144ba7
AM
2691 needed = *pneeded;
2692 if (needed)
116c20d2 2693 {
5d3236ee
DK
2694 /* Potentially, the add_archive_element hook may have set a
2695 substitute BFD for us. */
0e144ba7
AM
2696 if (abfd != oldbfd)
2697 {
2698 if (!info->keep_memory
2699 && !aout_link_free_symbols (oldbfd))
2700 return FALSE;
2701 if (!aout_get_external_symbols (abfd))
2702 return FALSE;
2703 }
2704 if (!aout_link_add_symbols (abfd, info))
116c20d2
NC
2705 return FALSE;
2706 }
2707
0e144ba7 2708 if (!info->keep_memory || !needed)
116c20d2 2709 {
0e144ba7 2710 if (!aout_link_free_symbols (abfd))
116c20d2
NC
2711 return FALSE;
2712 }
2713
2714 return TRUE;
2715}
2716
e135f41b
NC
2717/* Add all symbols from an object file to the hash table. */
2718
b34976b6 2719static bfd_boolean
116c20d2 2720aout_link_add_symbols (bfd *abfd, struct bfd_link_info *info)
e135f41b 2721{
b34976b6 2722 bfd_boolean (*add_one_symbol)
116c20d2
NC
2723 (struct bfd_link_info *, bfd *, const char *, flagword, asection *,
2724 bfd_vma, const char *, bfd_boolean, bfd_boolean,
2725 struct bfd_link_hash_entry **);
e135f41b
NC
2726 struct external_nlist *syms;
2727 bfd_size_type sym_count;
2728 char *strings;
b34976b6 2729 bfd_boolean copy;
e135f41b 2730 struct aout_link_hash_entry **sym_hash;
116c20d2 2731 struct external_nlist *p;
e135f41b
NC
2732 struct external_nlist *pend;
2733
2734 syms = obj_aout_external_syms (abfd);
2735 sym_count = obj_aout_external_sym_count (abfd);
2736 strings = obj_aout_external_strings (abfd);
2737 if (info->keep_memory)
b34976b6 2738 copy = FALSE;
e135f41b 2739 else
b34976b6 2740 copy = TRUE;
e135f41b
NC
2741
2742 if (aout_backend_info (abfd)->add_dynamic_symbols != NULL)
2743 {
2744 if (! ((*aout_backend_info (abfd)->add_dynamic_symbols)
2745 (abfd, info, &syms, &sym_count, &strings)))
b34976b6 2746 return FALSE;
e135f41b
NC
2747 }
2748
2749 /* We keep a list of the linker hash table entries that correspond
2750 to particular symbols. We could just look them up in the hash
2751 table, but keeping the list is more efficient. Perhaps this
2752 should be conditional on info->keep_memory. */
116c20d2
NC
2753 sym_hash = bfd_alloc (abfd,
2754 sym_count * sizeof (struct aout_link_hash_entry *));
e135f41b 2755 if (sym_hash == NULL && sym_count != 0)
b34976b6 2756 return FALSE;
e135f41b
NC
2757 obj_aout_sym_hashes (abfd) = sym_hash;
2758
2759 add_one_symbol = aout_backend_info (abfd)->add_one_symbol;
2760 if (add_one_symbol == NULL)
2761 add_one_symbol = _bfd_generic_link_add_one_symbol;
2762
2763 p = syms;
2764 pend = p + sym_count;
2765 for (; p < pend; p++, sym_hash++)
2766 {
2767 int type;
2768 const char *name;
2769 bfd_vma value;
2770 asection *section;
2771 flagword flags;
2772 const char *string;
2773
2774 *sym_hash = NULL;
2775
dc810e39 2776 type = H_GET_8 (abfd, p->e_type);
e135f41b 2777
e135f41b
NC
2778 name = strings + GET_WORD (abfd, p->e_strx);
2779 value = GET_WORD (abfd, p->e_value);
2780 flags = BSF_GLOBAL;
2781 string = NULL;
2782 switch (type)
2783 {
2784 default:
0c98115d
PK
2785 /* Anything else should be a debugging symbol. */
2786 BFD_ASSERT ((type & N_STAB) != 0);
2787 continue;
e135f41b
NC
2788
2789 case N_UNDF:
2790 case N_ABS:
2791 case N_TEXT:
2792 case N_DATA:
2793 case N_BSS:
2794 case N_REG:
2795 case N_FN:
2796 /* Ignore symbols that are not externally visible. */
2797 continue;
2798
2799 case N_UNDF | N_EXT:
2800 if (value == 0)
2801 {
2802 section = bfd_und_section_ptr;
2803 flags = 0;
2804 }
2805 else
2806 section = bfd_com_section_ptr;
2807 break;
2808 case N_ABS | N_EXT:
2809 section = bfd_abs_section_ptr;
2810 break;
2811 case N_TEXT | N_EXT:
2812 section = obj_textsec (abfd);
2813 value -= bfd_get_section_vma (abfd, section);
2814 break;
2815 case N_DATA | N_EXT:
2816 /* Treat N_SETV symbols as N_DATA symbol; see comment in
2817 translate_from_native_sym_flags. */
2818 section = obj_datasec (abfd);
2819 value -= bfd_get_section_vma (abfd, section);
2820 break;
2821 case N_BSS | N_EXT:
2822 section = obj_bsssec (abfd);
2823 value -= bfd_get_section_vma (abfd, section);
2824 break;
2825 }
2826
2827 if (! ((*add_one_symbol)
b34976b6 2828 (info, abfd, name, flags, section, value, string, copy, FALSE,
e135f41b 2829 (struct bfd_link_hash_entry **) sym_hash)))
b34976b6 2830 return FALSE;
e135f41b
NC
2831
2832 /* Restrict the maximum alignment of a common symbol based on
2833 the architecture, since a.out has no way to represent
2834 alignment requirements of a section in a .o file. FIXME:
2835 This isn't quite right: it should use the architecture of the
2836 output file, not the input files. */
2837 if ((*sym_hash)->root.type == bfd_link_hash_common
2838 && ((*sym_hash)->root.u.c.p->alignment_power >
2839 bfd_get_arch_info (abfd)->section_align_power))
2840 (*sym_hash)->root.u.c.p->alignment_power =
2841 bfd_get_arch_info (abfd)->section_align_power;
2842
2843 /* If this is a set symbol, and we are not building sets, then
2844 it is possible for the hash entry to not have been set. In
2845 such a case, treat the symbol as not globally defined. */
2846 if ((*sym_hash)->root.type == bfd_link_hash_new)
2847 {
2848 BFD_ASSERT ((flags & BSF_CONSTRUCTOR) != 0);
2849 *sym_hash = NULL;
2850 }
2851 }
2852
b34976b6 2853 return TRUE;
e135f41b
NC
2854}
2855\f
116c20d2 2856/* Look up an entry in an the header file hash table. */
e135f41b
NC
2857
2858#define aout_link_includes_lookup(table, string, create, copy) \
2859 ((struct aout_link_includes_entry *) \
2860 bfd_hash_lookup (&(table)->root, (string), (create), (copy)))
2861
e135f41b
NC
2862/* The function to create a new entry in the header file hash table. */
2863
2864static struct bfd_hash_entry *
116c20d2
NC
2865aout_link_includes_newfunc (struct bfd_hash_entry *entry,
2866 struct bfd_hash_table *table,
2867 const char *string)
e135f41b 2868{
116c20d2 2869 struct aout_link_includes_entry * ret =
e135f41b
NC
2870 (struct aout_link_includes_entry *) entry;
2871
2872 /* Allocate the structure if it has not already been allocated by a
2873 subclass. */
116c20d2
NC
2874 if (ret == NULL)
2875 ret = bfd_hash_allocate (table,
2876 sizeof (struct aout_link_includes_entry));
2877 if (ret == NULL)
2878 return NULL;
e135f41b
NC
2879
2880 /* Call the allocation method of the superclass. */
2881 ret = ((struct aout_link_includes_entry *)
2882 bfd_hash_newfunc ((struct bfd_hash_entry *) ret, table, string));
2883 if (ret)
116c20d2
NC
2884 /* Set local fields. */
2885 ret->totals = NULL;
e135f41b
NC
2886
2887 return (struct bfd_hash_entry *) ret;
2888}
2889
116c20d2 2890static bfd_boolean
7686d77d 2891aout_link_write_other_symbol (struct bfd_hash_entry *bh, void *data)
e135f41b 2892{
7686d77d 2893 struct aout_link_hash_entry *h = (struct aout_link_hash_entry *) bh;
57402f1e 2894 struct aout_final_link_info *flaginfo = (struct aout_final_link_info *) data;
116c20d2
NC
2895 bfd *output_bfd;
2896 int type;
2897 bfd_vma val;
2898 struct external_nlist outsym;
2899 bfd_size_type indx;
2900 bfd_size_type amt;
e135f41b 2901
116c20d2
NC
2902 if (h->root.type == bfd_link_hash_warning)
2903 {
2904 h = (struct aout_link_hash_entry *) h->root.u.i.link;
2905 if (h->root.type == bfd_link_hash_new)
2906 return TRUE;
2907 }
e135f41b 2908
57402f1e 2909 output_bfd = flaginfo->output_bfd;
e135f41b 2910
116c20d2 2911 if (aout_backend_info (output_bfd)->write_dynamic_symbol != NULL)
e135f41b 2912 {
116c20d2 2913 if (! ((*aout_backend_info (output_bfd)->write_dynamic_symbol)
57402f1e 2914 (output_bfd, flaginfo->info, h)))
e135f41b 2915 {
116c20d2
NC
2916 /* FIXME: No way to handle errors. */
2917 abort ();
e135f41b 2918 }
116c20d2 2919 }
e135f41b 2920
116c20d2
NC
2921 if (h->written)
2922 return TRUE;
e135f41b 2923
116c20d2 2924 h->written = TRUE;
e135f41b 2925
116c20d2
NC
2926 /* An indx of -2 means the symbol must be written. */
2927 if (h->indx != -2
57402f1e
NC
2928 && (flaginfo->info->strip == strip_all
2929 || (flaginfo->info->strip == strip_some
2930 && bfd_hash_lookup (flaginfo->info->keep_hash, h->root.root.string,
116c20d2
NC
2931 FALSE, FALSE) == NULL)))
2932 return TRUE;
e135f41b 2933
116c20d2 2934 switch (h->root.type)
e135f41b 2935 {
116c20d2
NC
2936 default:
2937 abort ();
2938 /* Avoid variable not initialized warnings. */
2939 return TRUE;
2940 case bfd_link_hash_new:
2941 /* This can happen for set symbols when sets are not being
07d6d2b8 2942 built. */
116c20d2
NC
2943 return TRUE;
2944 case bfd_link_hash_undefined:
2945 type = N_UNDF | N_EXT;
2946 val = 0;
2947 break;
2948 case bfd_link_hash_defined:
2949 case bfd_link_hash_defweak:
2950 {
2951 asection *sec;
2952
2953 sec = h->root.u.def.section->output_section;
2954 BFD_ASSERT (bfd_is_abs_section (sec)
2955 || sec->owner == output_bfd);
2956 if (sec == obj_textsec (output_bfd))
2957 type = h->root.type == bfd_link_hash_defined ? N_TEXT : N_WEAKT;
2958 else if (sec == obj_datasec (output_bfd))
2959 type = h->root.type == bfd_link_hash_defined ? N_DATA : N_WEAKD;
2960 else if (sec == obj_bsssec (output_bfd))
2961 type = h->root.type == bfd_link_hash_defined ? N_BSS : N_WEAKB;
2962 else
2963 type = h->root.type == bfd_link_hash_defined ? N_ABS : N_WEAKA;
2964 type |= N_EXT;
2965 val = (h->root.u.def.value
2966 + sec->vma
2967 + h->root.u.def.section->output_offset);
2968 }
2969 break;
2970 case bfd_link_hash_common:
2971 type = N_UNDF | N_EXT;
2972 val = h->root.u.c.size;
2973 break;
2974 case bfd_link_hash_undefweak:
2975 type = N_WEAKU;
2976 val = 0;
1a0670f3 2977 /* Fall through. */
116c20d2
NC
2978 case bfd_link_hash_indirect:
2979 case bfd_link_hash_warning:
2980 /* FIXME: Ignore these for now. The circumstances under which
2981 they should be written out are not clear to me. */
2982 return TRUE;
e135f41b
NC
2983 }
2984
116c20d2 2985 H_PUT_8 (output_bfd, type, outsym.e_type);
57402f1e 2986 indx = add_to_stringtab (output_bfd, flaginfo->strtab, h->root.root.string,
116c20d2
NC
2987 FALSE);
2988 if (indx == (bfd_size_type) -1)
2989 /* FIXME: No way to handle errors. */
2990 abort ();
e135f41b 2991
116c20d2
NC
2992 PUT_WORD (output_bfd, indx, outsym.e_strx);
2993 PUT_WORD (output_bfd, val, outsym.e_value);
e135f41b 2994
116c20d2 2995 amt = EXTERNAL_NLIST_SIZE;
57402f1e 2996 if (bfd_seek (output_bfd, flaginfo->symoff, SEEK_SET) != 0
116c20d2
NC
2997 || bfd_bwrite ((void *) &outsym, amt, output_bfd) != amt)
2998 /* FIXME: No way to handle errors. */
2999 abort ();
e135f41b 3000
57402f1e 3001 flaginfo->symoff += amt;
116c20d2
NC
3002 h->indx = obj_aout_external_sym_count (output_bfd);
3003 ++obj_aout_external_sym_count (output_bfd);
e135f41b 3004
116c20d2
NC
3005 return TRUE;
3006}
e135f41b 3007
116c20d2 3008/* Handle a link order which is supposed to generate a reloc. */
e135f41b 3009
116c20d2 3010static bfd_boolean
57402f1e 3011aout_link_reloc_link_order (struct aout_final_link_info *flaginfo,
116c20d2
NC
3012 asection *o,
3013 struct bfd_link_order *p)
3014{
3015 struct bfd_link_order_reloc *pr;
3016 int r_index;
3017 int r_extern;
3018 reloc_howto_type *howto;
3019 file_ptr *reloff_ptr;
3020 struct reloc_std_external srel;
3021 void * rel_ptr;
3022 bfd_size_type rel_size;
e135f41b 3023
116c20d2 3024 pr = p->u.reloc.p;
e135f41b 3025
116c20d2 3026 if (p->type == bfd_section_reloc_link_order)
e135f41b 3027 {
116c20d2
NC
3028 r_extern = 0;
3029 if (bfd_is_abs_section (pr->u.section))
3030 r_index = N_ABS | N_EXT;
3031 else
e135f41b 3032 {
57402f1e 3033 BFD_ASSERT (pr->u.section->owner == flaginfo->output_bfd);
116c20d2 3034 r_index = pr->u.section->target_index;
e135f41b
NC
3035 }
3036 }
116c20d2 3037 else
e135f41b 3038 {
116c20d2 3039 struct aout_link_hash_entry *h;
e135f41b 3040
116c20d2
NC
3041 BFD_ASSERT (p->type == bfd_symbol_reloc_link_order);
3042 r_extern = 1;
3043 h = ((struct aout_link_hash_entry *)
57402f1e 3044 bfd_wrapped_link_hash_lookup (flaginfo->output_bfd, flaginfo->info,
116c20d2
NC
3045 pr->u.name, FALSE, FALSE, TRUE));
3046 if (h != NULL
3047 && h->indx >= 0)
3048 r_index = h->indx;
3049 else if (h != NULL)
3050 {
3051 /* We decided to strip this symbol, but it turns out that we
3052 can't. Note that we lose the other and desc information
3053 here. I don't think that will ever matter for a global
3054 symbol. */
3055 h->indx = -2;
3056 h->written = FALSE;
57402f1e 3057 if (!aout_link_write_other_symbol (&h->root.root, flaginfo))
116c20d2
NC
3058 return FALSE;
3059 r_index = h->indx;
e135f41b 3060 }
116c20d2 3061 else
e135f41b 3062 {
1a72702b
AM
3063 (*flaginfo->info->callbacks->unattached_reloc)
3064 (flaginfo->info, pr->u.name, NULL, NULL, (bfd_vma) 0);
116c20d2 3065 r_index = 0;
e135f41b
NC
3066 }
3067 }
3068
57402f1e 3069 howto = bfd_reloc_type_lookup (flaginfo->output_bfd, pr->reloc);
116c20d2 3070 if (howto == 0)
e135f41b 3071 {
116c20d2
NC
3072 bfd_set_error (bfd_error_bad_value);
3073 return FALSE;
e135f41b
NC
3074 }
3075
57402f1e
NC
3076 if (o == obj_textsec (flaginfo->output_bfd))
3077 reloff_ptr = &flaginfo->treloff;
3078 else if (o == obj_datasec (flaginfo->output_bfd))
3079 reloff_ptr = &flaginfo->dreloff;
116c20d2
NC
3080 else
3081 abort ();
e135f41b 3082
116c20d2 3083#ifdef MY_put_reloc
57402f1e 3084 MY_put_reloc(flaginfo->output_bfd, r_extern, r_index, p->offset, howto,
116c20d2
NC
3085 &srel);
3086#else
3087 {
3088 int r_pcrel;
3089 int r_baserel;
3090 int r_jmptable;
3091 int r_relative;
3092 int r_length;
e135f41b 3093
116c20d2 3094 fprintf (stderr, "TODO: line %d in bfd/pdp11.c\n", __LINE__);
e135f41b 3095
116c20d2
NC
3096 r_pcrel = howto->pc_relative;
3097 r_baserel = (howto->type & 8) != 0;
3098 r_jmptable = (howto->type & 16) != 0;
3099 r_relative = (howto->type & 32) != 0;
3100 r_length = howto->size;
e135f41b 3101
57402f1e
NC
3102 PUT_WORD (flaginfo->output_bfd, p->offset, srel.r_address);
3103 if (bfd_header_big_endian (flaginfo->output_bfd))
116c20d2
NC
3104 {
3105 srel.r_index[0] = r_index >> 16;
3106 srel.r_index[1] = r_index >> 8;
3107 srel.r_index[2] = r_index;
3108 srel.r_type[0] =
3109 ((r_extern ? RELOC_STD_BITS_EXTERN_BIG : 0)
3110 | (r_pcrel ? RELOC_STD_BITS_PCREL_BIG : 0)
3111 | (r_baserel ? RELOC_STD_BITS_BASEREL_BIG : 0)
3112 | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_BIG : 0)
3113 | (r_relative ? RELOC_STD_BITS_RELATIVE_BIG : 0)
3114 | (r_length << RELOC_STD_BITS_LENGTH_SH_BIG));
3115 }
3116 else
3117 {
3118 srel.r_index[2] = r_index >> 16;
3119 srel.r_index[1] = r_index >> 8;
3120 srel.r_index[0] = r_index;
3121 srel.r_type[0] =
3122 ((r_extern ? RELOC_STD_BITS_EXTERN_LITTLE : 0)
3123 | (r_pcrel ? RELOC_STD_BITS_PCREL_LITTLE : 0)
3124 | (r_baserel ? RELOC_STD_BITS_BASEREL_LITTLE : 0)
3125 | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_LITTLE : 0)
3126 | (r_relative ? RELOC_STD_BITS_RELATIVE_LITTLE : 0)
3127 | (r_length << RELOC_STD_BITS_LENGTH_SH_LITTLE));
3128 }
3129 }
3130#endif
3131 rel_ptr = (void *) &srel;
e135f41b 3132
116c20d2
NC
3133 /* We have to write the addend into the object file, since
3134 standard a.out relocs are in place. It would be more
3135 reliable if we had the current contents of the file here,
3136 rather than assuming zeroes, but we can't read the file since
3137 it was opened using bfd_openw. */
3138 if (pr->addend != 0)
e135f41b 3139 {
116c20d2
NC
3140 bfd_size_type size;
3141 bfd_reloc_status_type r;
3142 bfd_byte *buf;
3143 bfd_boolean ok;
3144
3145 size = bfd_get_reloc_size (howto);
3146 buf = bfd_zmalloc (size);
6346d5ca 3147 if (buf == NULL && size != 0)
116c20d2 3148 return FALSE;
57402f1e 3149 r = MY_relocate_contents (howto, flaginfo->output_bfd,
116c20d2
NC
3150 pr->addend, buf);
3151 switch (r)
3152 {
3153 case bfd_reloc_ok:
3154 break;
3155 default:
3156 case bfd_reloc_outofrange:
3157 abort ();
3158 case bfd_reloc_overflow:
1a72702b
AM
3159 (*flaginfo->info->callbacks->reloc_overflow)
3160 (flaginfo->info, NULL,
3161 (p->type == bfd_section_reloc_link_order
3162 ? bfd_section_name (flaginfo->output_bfd,
3163 pr->u.section)
3164 : pr->u.name),
3165 howto->name, pr->addend, NULL,
3166 (asection *) NULL, (bfd_vma) 0);
116c20d2
NC
3167 break;
3168 }
57402f1e 3169 ok = bfd_set_section_contents (flaginfo->output_bfd, o,
116c20d2
NC
3170 (void *) buf,
3171 (file_ptr) p->offset,
3172 size);
3173 free (buf);
3174 if (! ok)
3175 return FALSE;
e135f41b
NC
3176 }
3177
57402f1e
NC
3178 rel_size = obj_reloc_entry_size (flaginfo->output_bfd);
3179 if (bfd_seek (flaginfo->output_bfd, *reloff_ptr, SEEK_SET) != 0
3180 || bfd_bwrite (rel_ptr, rel_size, flaginfo->output_bfd) != rel_size)
b34976b6 3181 return FALSE;
e135f41b 3182
116c20d2 3183 *reloff_ptr += rel_size;
e135f41b 3184
116c20d2
NC
3185 /* Assert that the relocs have not run into the symbols, and that n
3186 the text relocs have not run into the data relocs. */
57402f1e
NC
3187 BFD_ASSERT (*reloff_ptr <= obj_sym_filepos (flaginfo->output_bfd)
3188 && (reloff_ptr != &flaginfo->treloff
116c20d2 3189 || (*reloff_ptr
57402f1e 3190 <= obj_datasec (flaginfo->output_bfd)->rel_filepos)));
e135f41b 3191
116c20d2
NC
3192 return TRUE;
3193}
e135f41b 3194
116c20d2
NC
3195/* Get the section corresponding to a reloc index. */
3196
3197static inline asection *
3198aout_reloc_type_to_section (bfd *abfd, int type)
3199{
3200 switch (type)
e135f41b 3201 {
116c20d2
NC
3202 case RTEXT: return obj_textsec (abfd);
3203 case RDATA: return obj_datasec (abfd);
3204 case RBSS: return obj_bsssec (abfd);
3205 case RABS: return bfd_abs_section_ptr;
3206 case REXT: return bfd_und_section_ptr;
3207 default: abort ();
e135f41b 3208 }
e135f41b
NC
3209}
3210
b34976b6 3211static bfd_boolean
57402f1e 3212pdp11_aout_link_input_section (struct aout_final_link_info *flaginfo,
116c20d2
NC
3213 bfd *input_bfd,
3214 asection *input_section,
3215 bfd_byte *relocs,
3216 bfd_size_type rel_size,
3217 bfd_byte *contents)
e135f41b 3218{
116c20d2
NC
3219 bfd_boolean (*check_dynamic_reloc)
3220 (struct bfd_link_info *, bfd *, asection *,
3221 struct aout_link_hash_entry *, void *, bfd_byte *, bfd_boolean *,
3222 bfd_vma *);
e135f41b 3223 bfd *output_bfd;
116c20d2
NC
3224 bfd_boolean relocatable;
3225 struct external_nlist *syms;
e135f41b 3226 char *strings;
116c20d2 3227 struct aout_link_hash_entry **sym_hashes;
e135f41b 3228 int *symbol_map;
116c20d2
NC
3229 bfd_byte *rel;
3230 bfd_byte *rel_end;
e135f41b 3231
57402f1e 3232 output_bfd = flaginfo->output_bfd;
116c20d2 3233 check_dynamic_reloc = aout_backend_info (output_bfd)->check_dynamic_reloc;
e135f41b 3234
116c20d2
NC
3235 BFD_ASSERT (obj_reloc_entry_size (input_bfd) == RELOC_SIZE);
3236 BFD_ASSERT (input_bfd->xvec->header_byteorder
3237 == output_bfd->xvec->header_byteorder);
e135f41b 3238
0e1862bb 3239 relocatable = bfd_link_relocatable (flaginfo->info);
116c20d2
NC
3240 syms = obj_aout_external_syms (input_bfd);
3241 strings = obj_aout_external_strings (input_bfd);
3242 sym_hashes = obj_aout_sym_hashes (input_bfd);
57402f1e 3243 symbol_map = flaginfo->symbol_map;
116c20d2 3244
116c20d2
NC
3245 rel = relocs;
3246 rel_end = rel + rel_size;
3247 for (; rel < rel_end; rel += RELOC_SIZE)
e135f41b 3248 {
116c20d2
NC
3249 bfd_vma r_addr;
3250 int r_index;
3251 int r_type;
3252 int r_pcrel;
3253 int r_extern;
3254 reloc_howto_type *howto;
3255 struct aout_link_hash_entry *h = NULL;
3256 bfd_vma relocation;
3257 bfd_reloc_status_type r;
3258 int reloc_entry;
e135f41b 3259
116c20d2
NC
3260 reloc_entry = GET_WORD (input_bfd, (void *) rel);
3261 if (reloc_entry == 0)
e135f41b
NC
3262 continue;
3263
116c20d2
NC
3264 {
3265 unsigned int howto_idx;
e135f41b 3266
116c20d2
NC
3267 r_index = (reloc_entry & RIDXMASK) >> 4;
3268 r_type = reloc_entry & RTYPE;
3269 r_pcrel = reloc_entry & RELFLG;
3270 r_addr = (char *) rel - (char *) relocs;
e135f41b 3271
116c20d2 3272 r_extern = (r_type == REXT);
e135f41b 3273
116c20d2
NC
3274 howto_idx = r_pcrel;
3275 BFD_ASSERT (howto_idx < TABLE_SIZE (howto_table_pdp11));
3276 howto = howto_table_pdp11 + howto_idx;
3277 }
3278
3279 if (relocatable)
e135f41b 3280 {
116c20d2
NC
3281 /* We are generating a relocatable output file, and must
3282 modify the reloc accordingly. */
3283 if (r_extern)
3284 {
3285 /* If we know the symbol this relocation is against,
3286 convert it into a relocation against a section. This
3287 is what the native linker does. */
3288 h = sym_hashes[r_index];
3289 if (h != NULL
3290 && (h->root.type == bfd_link_hash_defined
3291 || h->root.type == bfd_link_hash_defweak))
3292 {
3293 asection *output_section;
e135f41b 3294
116c20d2
NC
3295 /* Compute a new r_index. */
3296 output_section = h->root.u.def.section->output_section;
e135f41b 3297 if (output_section == obj_textsec (output_bfd))
116c20d2 3298 r_type = N_TEXT;
e135f41b 3299 else if (output_section == obj_datasec (output_bfd))
116c20d2 3300 r_type = N_DATA;
e135f41b 3301 else if (output_section == obj_bsssec (output_bfd))
116c20d2 3302 r_type = N_BSS;
e135f41b 3303 else
116c20d2 3304 r_type = N_ABS;
e135f41b 3305
116c20d2
NC
3306 /* Add the symbol value and the section VMA to the
3307 addend stored in the contents. */
3308 relocation = (h->root.u.def.value
3309 + output_section->vma
3310 + h->root.u.def.section->output_offset);
e135f41b 3311 }
116c20d2 3312 else
e135f41b 3313 {
116c20d2
NC
3314 /* We must change r_index according to the symbol
3315 map. */
3316 r_index = symbol_map[r_index];
e135f41b 3317
116c20d2 3318 if (r_index == -1)
e135f41b 3319 {
116c20d2 3320 if (h != NULL)
e135f41b 3321 {
116c20d2 3322 /* We decided to strip this symbol, but it
07d6d2b8
AM
3323 turns out that we can't. Note that we
3324 lose the other and desc information here.
3325 I don't think that will ever matter for a
3326 global symbol. */
116c20d2 3327 if (h->indx < 0)
e135f41b 3328 {
116c20d2
NC
3329 h->indx = -2;
3330 h->written = FALSE;
7686d77d 3331 if (!aout_link_write_other_symbol (&h->root.root,
57402f1e 3332 flaginfo))
116c20d2 3333 return FALSE;
e135f41b 3334 }
116c20d2
NC
3335 r_index = h->indx;
3336 }
3337 else
3338 {
3339 const char *name;
3340
3341 name = strings + GET_WORD (input_bfd,
3342 syms[r_index].e_strx);
1a72702b
AM
3343 (*flaginfo->info->callbacks->unattached_reloc)
3344 (flaginfo->info, name, input_bfd, input_section,
3345 r_addr);
116c20d2 3346 r_index = 0;
e135f41b
NC
3347 }
3348 }
116c20d2
NC
3349
3350 relocation = 0;
e135f41b
NC
3351 }
3352
116c20d2
NC
3353 /* Write out the new r_index value. */
3354 reloc_entry = GET_WORD (input_bfd, rel);
3355 reloc_entry &= RIDXMASK;
3356 reloc_entry |= r_index << 4;
3357 PUT_WORD (input_bfd, reloc_entry, rel);
3358 }
3359 else
3360 {
3361 asection *section;
3362
3363 /* This is a relocation against a section. We must
3364 adjust by the amount that the section moved. */
3365 section = aout_reloc_type_to_section (input_bfd, r_type);
3366 relocation = (section->output_section->vma
3367 + section->output_offset
3368 - section->vma);
3369 }
3370
3371 /* Change the address of the relocation. */
3372 fprintf (stderr, "TODO: change the address of the relocation\n");
3373
3374 /* Adjust a PC relative relocation by removing the reference
3375 to the original address in the section and including the
3376 reference to the new address. */
3377 if (r_pcrel)
3378 relocation -= (input_section->output_section->vma
3379 + input_section->output_offset
3380 - input_section->vma);
3381
3382#ifdef MY_relocatable_reloc
3383 MY_relocatable_reloc (howto, output_bfd, rel, relocation, r_addr);
3384#endif
3385
3386 if (relocation == 0)
3387 r = bfd_reloc_ok;
3388 else
3389 r = MY_relocate_contents (howto,
3390 input_bfd, relocation,
3391 contents + r_addr);
3392 }
3393 else
3394 {
3395 bfd_boolean hundef;
3396
3397 /* We are generating an executable, and must do a full
3398 relocation. */
3399 hundef = FALSE;
3400 if (r_extern)
3401 {
3402 h = sym_hashes[r_index];
3403
3404 if (h != NULL
3405 && (h->root.type == bfd_link_hash_defined
3406 || h->root.type == bfd_link_hash_defweak))
e135f41b 3407 {
116c20d2
NC
3408 relocation = (h->root.u.def.value
3409 + h->root.u.def.section->output_section->vma
3410 + h->root.u.def.section->output_offset);
e135f41b 3411 }
116c20d2
NC
3412 else if (h != NULL
3413 && h->root.type == bfd_link_hash_undefweak)
3414 relocation = 0;
e135f41b
NC
3415 else
3416 {
116c20d2
NC
3417 hundef = TRUE;
3418 relocation = 0;
3419 }
3420 }
3421 else
3422 {
3423 asection *section;
e135f41b 3424
116c20d2
NC
3425 section = aout_reloc_type_to_section (input_bfd, r_type);
3426 relocation = (section->output_section->vma
3427 + section->output_offset
3428 - section->vma);
3429 if (r_pcrel)
3430 relocation += input_section->vma;
3431 }
e135f41b 3432
116c20d2
NC
3433 if (check_dynamic_reloc != NULL)
3434 {
3435 bfd_boolean skip;
e135f41b 3436
116c20d2 3437 if (! ((*check_dynamic_reloc)
57402f1e 3438 (flaginfo->info, input_bfd, input_section, h,
116c20d2
NC
3439 (void *) rel, contents, &skip, &relocation)))
3440 return FALSE;
3441 if (skip)
3442 continue;
3443 }
3444
3445 /* Now warn if a global symbol is undefined. We could not
07d6d2b8
AM
3446 do this earlier, because check_dynamic_reloc might want
3447 to skip this reloc. */
0e1862bb 3448 if (hundef && ! bfd_link_pic (flaginfo->info))
116c20d2
NC
3449 {
3450 const char *name;
3451
3452 if (h != NULL)
3453 name = h->root.root.string;
3454 else
3455 name = strings + GET_WORD (input_bfd, syms[r_index].e_strx);
1a72702b
AM
3456 (*flaginfo->info->callbacks->undefined_symbol)
3457 (flaginfo->info, name, input_bfd, input_section,
3458 r_addr, TRUE);
e135f41b 3459 }
116c20d2
NC
3460
3461 r = MY_final_link_relocate (howto,
3462 input_bfd, input_section,
3463 contents, r_addr, relocation,
3464 (bfd_vma) 0);
e135f41b
NC
3465 }
3466
116c20d2 3467 if (r != bfd_reloc_ok)
e135f41b 3468 {
116c20d2
NC
3469 switch (r)
3470 {
3471 default:
3472 case bfd_reloc_outofrange:
3473 abort ();
3474 case bfd_reloc_overflow:
3475 {
3476 const char *name;
3477
3478 if (h != NULL)
3479 name = NULL;
3480 else if (r_extern)
3481 name = strings + GET_WORD (input_bfd,
3482 syms[r_index].e_strx);
3483 else
3484 {
3485 asection *s;
3486
3487 s = aout_reloc_type_to_section (input_bfd, r_type);
3488 name = bfd_section_name (input_bfd, s);
3489 }
1a72702b
AM
3490 (*flaginfo->info->callbacks->reloc_overflow)
3491 (flaginfo->info, (h ? &h->root : NULL), name, howto->name,
3492 (bfd_vma) 0, input_bfd, input_section, r_addr);
116c20d2
NC
3493 }
3494 break;
3495 }
e135f41b 3496 }
e135f41b
NC
3497 }
3498
116c20d2
NC
3499 return TRUE;
3500}
3501
3502/* Link an a.out section into the output file. */
3503
3504static bfd_boolean
57402f1e 3505aout_link_input_section (struct aout_final_link_info *flaginfo,
116c20d2
NC
3506 bfd *input_bfd,
3507 asection *input_section,
3508 file_ptr *reloff_ptr,
3509 bfd_size_type rel_size)
3510{
3511 bfd_size_type input_size;
3512 void * relocs;
3513
3514 /* Get the section contents. */
3515 input_size = input_section->size;
3516 if (! bfd_get_section_contents (input_bfd, input_section,
57402f1e 3517 (void *) flaginfo->contents,
116c20d2
NC
3518 (file_ptr) 0, input_size))
3519 return FALSE;
3520
3521 /* Read in the relocs if we haven't already done it. */
3522 if (aout_section_data (input_section) != NULL
3523 && aout_section_data (input_section)->relocs != NULL)
3524 relocs = aout_section_data (input_section)->relocs;
3525 else
e135f41b 3526 {
57402f1e 3527 relocs = flaginfo->relocs;
116c20d2
NC
3528 if (rel_size > 0)
3529 {
3530 if (bfd_seek (input_bfd, input_section->rel_filepos, SEEK_SET) != 0
3531 || bfd_bread (relocs, rel_size, input_bfd) != rel_size)
3532 return FALSE;
3533 }
3534 }
e135f41b 3535
116c20d2 3536 /* Relocate the section contents. */
57402f1e 3537 if (! pdp11_aout_link_input_section (flaginfo, input_bfd, input_section,
116c20d2 3538 (bfd_byte *) relocs,
57402f1e 3539 rel_size, flaginfo->contents))
116c20d2
NC
3540 return FALSE;
3541
3542 /* Write out the section contents. */
57402f1e 3543 if (! bfd_set_section_contents (flaginfo->output_bfd,
116c20d2 3544 input_section->output_section,
57402f1e 3545 (void *) flaginfo->contents,
116c20d2
NC
3546 (file_ptr) input_section->output_offset,
3547 input_size))
3548 return FALSE;
3549
3550 /* If we are producing relocatable output, the relocs were
3551 modified, and we now write them out. */
0e1862bb 3552 if (bfd_link_relocatable (flaginfo->info) && rel_size > 0)
116c20d2 3553 {
57402f1e 3554 if (bfd_seek (flaginfo->output_bfd, *reloff_ptr, SEEK_SET) != 0)
116c20d2 3555 return FALSE;
57402f1e 3556 if (bfd_bwrite (relocs, rel_size, flaginfo->output_bfd) != rel_size)
116c20d2
NC
3557 return FALSE;
3558 *reloff_ptr += rel_size;
3559
3560 /* Assert that the relocs have not run into the symbols, and
3561 that if these are the text relocs they have not run into the
3562 data relocs. */
57402f1e
NC
3563 BFD_ASSERT (*reloff_ptr <= obj_sym_filepos (flaginfo->output_bfd)
3564 && (reloff_ptr != &flaginfo->treloff
116c20d2 3565 || (*reloff_ptr
57402f1e 3566 <= obj_datasec (flaginfo->output_bfd)->rel_filepos)));
116c20d2
NC
3567 }
3568
3569 return TRUE;
3570}
3571
3572/* Link an a.out input BFD into the output file. */
3573
3574static bfd_boolean
57402f1e 3575aout_link_input_bfd (struct aout_final_link_info *flaginfo, bfd *input_bfd)
116c20d2 3576{
116c20d2
NC
3577 BFD_ASSERT (bfd_get_format (input_bfd) == bfd_object);
3578
3579 /* If this is a dynamic object, it may need special handling. */
3580 if ((input_bfd->flags & DYNAMIC) != 0
3581 && aout_backend_info (input_bfd)->link_dynamic_object != NULL)
3582 return ((*aout_backend_info (input_bfd)->link_dynamic_object)
57402f1e 3583 (flaginfo->info, input_bfd));
116c20d2
NC
3584
3585 /* Get the symbols. We probably have them already, unless
57402f1e 3586 flaginfo->info->keep_memory is FALSE. */
116c20d2
NC
3587 if (! aout_get_external_symbols (input_bfd))
3588 return FALSE;
3589
116c20d2 3590 /* Write out the symbols and get a map of the new indices. The map
57402f1e
NC
3591 is placed into flaginfo->symbol_map. */
3592 if (! aout_link_write_symbols (flaginfo, input_bfd))
116c20d2
NC
3593 return FALSE;
3594
3595 /* Relocate and write out the sections. These functions use the
3596 symbol map created by aout_link_write_symbols. The linker_mark
3597 field will be set if these sections are to be included in the
3598 link, which will normally be the case. */
3599 if (obj_textsec (input_bfd)->linker_mark)
3600 {
57402f1e 3601 if (! aout_link_input_section (flaginfo, input_bfd,
116c20d2 3602 obj_textsec (input_bfd),
57402f1e 3603 &flaginfo->treloff,
116c20d2
NC
3604 exec_hdr (input_bfd)->a_trsize))
3605 return FALSE;
3606 }
3607 if (obj_datasec (input_bfd)->linker_mark)
3608 {
57402f1e 3609 if (! aout_link_input_section (flaginfo, input_bfd,
116c20d2 3610 obj_datasec (input_bfd),
57402f1e 3611 &flaginfo->dreloff,
116c20d2 3612 exec_hdr (input_bfd)->a_drsize))
b34976b6 3613 return FALSE;
116c20d2
NC
3614 }
3615
3616 /* If we are not keeping memory, we don't need the symbols any
3617 longer. We still need them if we are keeping memory, because the
3618 strings in the hash table point into them. */
57402f1e 3619 if (! flaginfo->info->keep_memory)
116c20d2
NC
3620 {
3621 if (! aout_link_free_symbols (input_bfd))
b34976b6 3622 return FALSE;
e135f41b
NC
3623 }
3624
b34976b6 3625 return TRUE;
e135f41b
NC
3626}
3627
116c20d2
NC
3628/* Do the final link step. This is called on the output BFD. The
3629 INFO structure should point to a list of BFDs linked through the
c72f2fb2 3630 link.next field which can be used to find each BFD which takes part
116c20d2
NC
3631 in the output. Also, each section in ABFD should point to a list
3632 of bfd_link_order structures which list all the input sections for
3633 the output section. */
e135f41b 3634
116c20d2
NC
3635bfd_boolean
3636NAME (aout, final_link) (bfd *abfd,
3637 struct bfd_link_info *info,
3638 void (*callback) (bfd *, file_ptr *, file_ptr *, file_ptr *))
e135f41b 3639{
116c20d2
NC
3640 struct aout_final_link_info aout_info;
3641 bfd_boolean includes_hash_initialized = FALSE;
3642 bfd *sub;
3643 bfd_size_type trsize, drsize;
3644 bfd_size_type max_contents_size;
3645 bfd_size_type max_relocs_size;
3646 bfd_size_type max_sym_count;
116c20d2
NC
3647 struct bfd_link_order *p;
3648 asection *o;
3649 bfd_boolean have_link_order_relocs;
e135f41b 3650
0e1862bb 3651 if (bfd_link_pic (info))
116c20d2 3652 abfd->flags |= DYNAMIC;
e92d460e 3653
116c20d2
NC
3654 aout_info.info = info;
3655 aout_info.output_bfd = abfd;
3656 aout_info.contents = NULL;
3657 aout_info.relocs = NULL;
3658 aout_info.symbol_map = NULL;
3659 aout_info.output_syms = NULL;
e135f41b 3660
66eb6687
AM
3661 if (!bfd_hash_table_init_n (&aout_info.includes.root,
3662 aout_link_includes_newfunc,
3663 sizeof (struct aout_link_includes_entry),
3664 251))
116c20d2
NC
3665 goto error_return;
3666 includes_hash_initialized = TRUE;
3667
3668 /* Figure out the largest section size. Also, if generating
3669 relocatable output, count the relocs. */
3670 trsize = 0;
3671 drsize = 0;
3672 max_contents_size = 0;
3673 max_relocs_size = 0;
3674 max_sym_count = 0;
c72f2fb2 3675 for (sub = info->input_bfds; sub != NULL; sub = sub->link.next)
e135f41b 3676 {
116c20d2
NC
3677 size_t sz;
3678
0e1862bb 3679 if (bfd_link_relocatable (info))
e135f41b 3680 {
116c20d2
NC
3681 if (bfd_get_flavour (sub) == bfd_target_aout_flavour)
3682 {
3683 trsize += exec_hdr (sub)->a_trsize;
3684 drsize += exec_hdr (sub)->a_drsize;
3685 }
3686 else
3687 {
3688 /* FIXME: We need to identify the .text and .data sections
3689 and call get_reloc_upper_bound and canonicalize_reloc to
3690 work out the number of relocs needed, and then multiply
3691 by the reloc size. */
4eca0228 3692 _bfd_error_handler
695344c0 3693 /* xgettext:c-format */
871b3ab2 3694 (_("%pB: relocatable link from %s to %s not supported"),
dae82561 3695 abfd, sub->xvec->name, abfd->xvec->name);
116c20d2
NC
3696 bfd_set_error (bfd_error_invalid_operation);
3697 goto error_return;
3698 }
e135f41b 3699 }
e135f41b 3700
116c20d2
NC
3701 if (bfd_get_flavour (sub) == bfd_target_aout_flavour)
3702 {
3703 sz = obj_textsec (sub)->size;
3704 if (sz > max_contents_size)
3705 max_contents_size = sz;
3706 sz = obj_datasec (sub)->size;
3707 if (sz > max_contents_size)
3708 max_contents_size = sz;
e135f41b 3709
116c20d2
NC
3710 sz = exec_hdr (sub)->a_trsize;
3711 if (sz > max_relocs_size)
3712 max_relocs_size = sz;
3713 sz = exec_hdr (sub)->a_drsize;
3714 if (sz > max_relocs_size)
3715 max_relocs_size = sz;
e135f41b 3716
116c20d2
NC
3717 sz = obj_aout_external_sym_count (sub);
3718 if (sz > max_sym_count)
3719 max_sym_count = sz;
3720 }
e135f41b
NC
3721 }
3722
0e1862bb 3723 if (bfd_link_relocatable (info))
e135f41b 3724 {
116c20d2
NC
3725 if (obj_textsec (abfd) != NULL)
3726 trsize += (_bfd_count_link_order_relocs (obj_textsec (abfd)
8423293d 3727 ->map_head.link_order)
116c20d2
NC
3728 * obj_reloc_entry_size (abfd));
3729 if (obj_datasec (abfd) != NULL)
3730 drsize += (_bfd_count_link_order_relocs (obj_datasec (abfd)
8423293d 3731 ->map_head.link_order)
116c20d2 3732 * obj_reloc_entry_size (abfd));
e135f41b 3733 }
e135f41b 3734
116c20d2
NC
3735 exec_hdr (abfd)->a_trsize = trsize;
3736 exec_hdr (abfd)->a_drsize = drsize;
3737 exec_hdr (abfd)->a_entry = bfd_get_start_address (abfd);
3738
3739 /* Adjust the section sizes and vmas according to the magic number.
3740 This sets a_text, a_data and a_bss in the exec_hdr and sets the
3741 filepos for each section. */
3a8c4a5b 3742 if (! NAME (aout, adjust_sizes_and_vmas) (abfd))
116c20d2
NC
3743 goto error_return;
3744
3745 /* The relocation and symbol file positions differ among a.out
3746 targets. We are passed a callback routine from the backend
3747 specific code to handle this.
3748 FIXME: At this point we do not know how much space the symbol
3749 table will require. This will not work for any (nonstandard)
3750 a.out target that needs to know the symbol table size before it
dc12032b 3751 can compute the relocation file positions. */
116c20d2
NC
3752 (*callback) (abfd, &aout_info.treloff, &aout_info.dreloff,
3753 &aout_info.symoff);
3754 obj_textsec (abfd)->rel_filepos = aout_info.treloff;
3755 obj_datasec (abfd)->rel_filepos = aout_info.dreloff;
3756 obj_sym_filepos (abfd) = aout_info.symoff;
3757
3758 /* We keep a count of the symbols as we output them. */
3759 obj_aout_external_sym_count (abfd) = 0;
3760
3761 /* We accumulate the string table as we write out the symbols. */
3762 aout_info.strtab = _bfd_stringtab_init ();
3763 if (aout_info.strtab == NULL)
3764 goto error_return;
3765
3766 /* Allocate buffers to hold section contents and relocs. */
3767 aout_info.contents = bfd_malloc (max_contents_size);
3768 aout_info.relocs = bfd_malloc (max_relocs_size);
3769 aout_info.symbol_map = bfd_malloc (max_sym_count * sizeof (int *));
3770 aout_info.output_syms = bfd_malloc ((max_sym_count + 1)
3771 * sizeof (struct external_nlist));
3772 if ((aout_info.contents == NULL && max_contents_size != 0)
3773 || (aout_info.relocs == NULL && max_relocs_size != 0)
3774 || (aout_info.symbol_map == NULL && max_sym_count != 0)
3775 || aout_info.output_syms == NULL)
3776 goto error_return;
3777
3778 /* If we have a symbol named __DYNAMIC, force it out now. This is
3779 required by SunOS. Doing this here rather than in sunos.c is a
3780 hack, but it's easier than exporting everything which would be
3781 needed. */
3782 {
3783 struct aout_link_hash_entry *h;
3784
3785 h = aout_link_hash_lookup (aout_hash_table (info), "__DYNAMIC",
3786 FALSE, FALSE, FALSE);
3787 if (h != NULL)
7686d77d 3788 aout_link_write_other_symbol (&h->root.root, &aout_info);
116c20d2
NC
3789 }
3790
3791 /* The most time efficient way to do the link would be to read all
3792 the input object files into memory and then sort out the
3793 information into the output file. Unfortunately, that will
3794 probably use too much memory. Another method would be to step
3795 through everything that composes the text section and write it
3796 out, and then everything that composes the data section and write
3797 it out, and then write out the relocs, and then write out the
3798 symbols. Unfortunately, that requires reading stuff from each
3799 input file several times, and we will not be able to keep all the
3800 input files open simultaneously, and reopening them will be slow.
3801
3802 What we do is basically process one input file at a time. We do
3803 everything we need to do with an input file once--copy over the
3804 section contents, handle the relocation information, and write
3805 out the symbols--and then we throw away the information we read
3806 from it. This approach requires a lot of lseeks of the output
3807 file, which is unfortunate but still faster than reopening a lot
3808 of files.
3809
3810 We use the output_has_begun field of the input BFDs to see
3811 whether we have already handled it. */
c72f2fb2 3812 for (sub = info->input_bfds; sub != NULL; sub = sub->link.next)
116c20d2
NC
3813 sub->output_has_begun = FALSE;
3814
3815 /* Mark all sections which are to be included in the link. This
3816 will normally be every section. We need to do this so that we
3817 can identify any sections which the linker has decided to not
3818 include. */
3819 for (o = abfd->sections; o != NULL; o = o->next)
e135f41b 3820 {
8423293d 3821 for (p = o->map_head.link_order; p != NULL; p = p->next)
116c20d2
NC
3822 if (p->type == bfd_indirect_link_order)
3823 p->u.indirect.section->linker_mark = TRUE;
e135f41b
NC
3824 }
3825
116c20d2
NC
3826 have_link_order_relocs = FALSE;
3827 for (o = abfd->sections; o != NULL; o = o->next)
3828 {
8423293d 3829 for (p = o->map_head.link_order;
116c20d2
NC
3830 p != NULL;
3831 p = p->next)
3832 {
3833 if (p->type == bfd_indirect_link_order
3834 && (bfd_get_flavour (p->u.indirect.section->owner)
3835 == bfd_target_aout_flavour))
3836 {
3837 bfd *input_bfd;
e135f41b 3838
116c20d2
NC
3839 input_bfd = p->u.indirect.section->owner;
3840 if (! input_bfd->output_has_begun)
3841 {
3842 if (! aout_link_input_bfd (&aout_info, input_bfd))
3843 goto error_return;
3844 input_bfd->output_has_begun = TRUE;
3845 }
3846 }
3847 else if (p->type == bfd_section_reloc_link_order
3848 || p->type == bfd_symbol_reloc_link_order)
3849 /* These are handled below. */
3850 have_link_order_relocs = TRUE;
3851 else
3852 {
3853 if (! _bfd_default_link_order (abfd, info, o, p))
3854 goto error_return;
3855 }
3856 }
3857 }
e135f41b 3858
116c20d2 3859 /* Write out any symbols that we have not already written out. */
7686d77d
AM
3860 bfd_hash_traverse (&info->hash->table,
3861 aout_link_write_other_symbol,
3862 &aout_info);
e135f41b 3863
116c20d2
NC
3864 /* Now handle any relocs we were asked to create by the linker.
3865 These did not come from any input file. We must do these after
3866 we have written out all the symbols, so that we know the symbol
3867 indices to use. */
3868 if (have_link_order_relocs)
e135f41b 3869 {
116c20d2 3870 for (o = abfd->sections; o != NULL; o = o->next)
e135f41b 3871 {
8423293d 3872 for (p = o->map_head.link_order;
116c20d2
NC
3873 p != NULL;
3874 p = p->next)
3875 {
3876 if (p->type == bfd_section_reloc_link_order
3877 || p->type == bfd_symbol_reloc_link_order)
3878 {
3879 if (! aout_link_reloc_link_order (&aout_info, o, p))
3880 goto error_return;
3881 }
3882 }
e135f41b
NC
3883 }
3884 }
3885
116c20d2
NC
3886 if (aout_info.contents != NULL)
3887 {
3888 free (aout_info.contents);
3889 aout_info.contents = NULL;
3890 }
3891 if (aout_info.relocs != NULL)
3892 {
3893 free (aout_info.relocs);
3894 aout_info.relocs = NULL;
3895 }
3896 if (aout_info.symbol_map != NULL)
3897 {
3898 free (aout_info.symbol_map);
3899 aout_info.symbol_map = NULL;
3900 }
3901 if (aout_info.output_syms != NULL)
3902 {
3903 free (aout_info.output_syms);
3904 aout_info.output_syms = NULL;
3905 }
3906 if (includes_hash_initialized)
3907 {
3908 bfd_hash_table_free (&aout_info.includes.root);
3909 includes_hash_initialized = FALSE;
3910 }
e135f41b 3911
116c20d2
NC
3912 /* Finish up any dynamic linking we may be doing. */
3913 if (aout_backend_info (abfd)->finish_dynamic_link != NULL)
3914 {
3915 if (! (*aout_backend_info (abfd)->finish_dynamic_link) (abfd, info))
3916 goto error_return;
3917 }
e135f41b 3918
116c20d2
NC
3919 /* Update the header information. */
3920 abfd->symcount = obj_aout_external_sym_count (abfd);
3921 exec_hdr (abfd)->a_syms = abfd->symcount * EXTERNAL_NLIST_SIZE;
3922 obj_str_filepos (abfd) = obj_sym_filepos (abfd) + exec_hdr (abfd)->a_syms;
3923 obj_textsec (abfd)->reloc_count =
3924 exec_hdr (abfd)->a_trsize / obj_reloc_entry_size (abfd);
3925 obj_datasec (abfd)->reloc_count =
3926 exec_hdr (abfd)->a_drsize / obj_reloc_entry_size (abfd);
3927
3928 /* Write out the string table, unless there are no symbols. */
3929 if (abfd->symcount > 0)
e135f41b 3930 {
116c20d2
NC
3931 if (bfd_seek (abfd, obj_str_filepos (abfd), SEEK_SET) != 0
3932 || ! emit_stringtab (abfd, aout_info.strtab))
3933 goto error_return;
3934 }
3935 else if (obj_textsec (abfd)->reloc_count == 0
3936 && obj_datasec (abfd)->reloc_count == 0)
3937 {
3938 bfd_byte b;
e135f41b 3939
116c20d2
NC
3940 b = 0;
3941 if (bfd_seek (abfd,
3942 (file_ptr) (obj_datasec (abfd)->filepos
3943 + exec_hdr (abfd)->a_data
3944 - 1),
3945 SEEK_SET) != 0
3946 || bfd_bwrite (&b, (bfd_size_type) 1, abfd) != 1)
3947 goto error_return;
e135f41b
NC
3948 }
3949
b34976b6 3950 return TRUE;
e135f41b 3951
116c20d2
NC
3952 error_return:
3953 if (aout_info.contents != NULL)
3954 free (aout_info.contents);
3955 if (aout_info.relocs != NULL)
3956 free (aout_info.relocs);
3957 if (aout_info.symbol_map != NULL)
3958 free (aout_info.symbol_map);
3959 if (aout_info.output_syms != NULL)
3960 free (aout_info.output_syms);
3961 if (includes_hash_initialized)
3962 bfd_hash_table_free (&aout_info.includes.root);
3963 return FALSE;
e135f41b
NC
3964}
3965
116c20d2
NC
3966/* Adjust and write out the symbols for an a.out file. Set the new
3967 symbol indices into a symbol_map. */
3968
b34976b6 3969static bfd_boolean
57402f1e 3970aout_link_write_symbols (struct aout_final_link_info *flaginfo, bfd *input_bfd)
e135f41b 3971{
e135f41b 3972 bfd *output_bfd;
116c20d2 3973 bfd_size_type sym_count;
e135f41b 3974 char *strings;
116c20d2
NC
3975 enum bfd_link_strip strip;
3976 enum bfd_link_discard discard;
3977 struct external_nlist *outsym;
3978 bfd_size_type strtab_index;
3979 struct external_nlist *sym;
3980 struct external_nlist *sym_end;
3981 struct aout_link_hash_entry **sym_hash;
e135f41b 3982 int *symbol_map;
116c20d2
NC
3983 bfd_boolean pass;
3984 bfd_boolean skip_next;
e135f41b 3985
57402f1e 3986 output_bfd = flaginfo->output_bfd;
116c20d2 3987 sym_count = obj_aout_external_sym_count (input_bfd);
e135f41b 3988 strings = obj_aout_external_strings (input_bfd);
57402f1e
NC
3989 strip = flaginfo->info->strip;
3990 discard = flaginfo->info->discard;
3991 outsym = flaginfo->output_syms;
e135f41b 3992
116c20d2
NC
3993 /* First write out a symbol for this object file, unless we are
3994 discarding such symbols. */
3995 if (strip != strip_all
3996 && (strip != strip_some
57402f1e 3997 || bfd_hash_lookup (flaginfo->info->keep_hash, input_bfd->filename,
116c20d2
NC
3998 FALSE, FALSE) != NULL)
3999 && discard != discard_all)
4000 {
4001 H_PUT_8 (output_bfd, N_TEXT, outsym->e_type);
57402f1e 4002 strtab_index = add_to_stringtab (output_bfd, flaginfo->strtab,
116c20d2
NC
4003 input_bfd->filename, FALSE);
4004 if (strtab_index == (bfd_size_type) -1)
4005 return FALSE;
4006 PUT_WORD (output_bfd, strtab_index, outsym->e_strx);
4007 PUT_WORD (output_bfd,
4008 (bfd_get_section_vma (output_bfd,
4009 obj_textsec (input_bfd)->output_section)
4010 + obj_textsec (input_bfd)->output_offset),
4011 outsym->e_value);
4012 ++obj_aout_external_sym_count (output_bfd);
4013 ++outsym;
4014 }
4015
4016 pass = FALSE;
4017 skip_next = FALSE;
4018 sym = obj_aout_external_syms (input_bfd);
4019 sym_end = sym + sym_count;
4020 sym_hash = obj_aout_sym_hashes (input_bfd);
57402f1e 4021 symbol_map = flaginfo->symbol_map;
116c20d2
NC
4022 memset (symbol_map, 0, (size_t) sym_count * sizeof *symbol_map);
4023 for (; sym < sym_end; sym++, sym_hash++, symbol_map++)
e135f41b 4024 {
116c20d2
NC
4025 const char *name;
4026 int type;
4027 struct aout_link_hash_entry *h;
4028 bfd_boolean skip;
4029 asection *symsec;
4030 bfd_vma val = 0;
4031 bfd_boolean copy;
e135f41b 4032
116c20d2 4033 /* We set *symbol_map to 0 above for all symbols. If it has
07d6d2b8
AM
4034 already been set to -1 for this symbol, it means that we are
4035 discarding it because it appears in a duplicate header file.
4036 See the N_BINCL code below. */
116c20d2 4037 if (*symbol_map == -1)
e135f41b
NC
4038 continue;
4039
116c20d2 4040 /* Initialize *symbol_map to -1, which means that the symbol was
07d6d2b8
AM
4041 not copied into the output file. We will change it later if
4042 we do copy the symbol over. */
116c20d2 4043 *symbol_map = -1;
e135f41b 4044
116c20d2
NC
4045 type = H_GET_8 (input_bfd, sym->e_type);
4046 name = strings + GET_WORD (input_bfd, sym->e_strx);
e135f41b 4047
116c20d2 4048 h = NULL;
e135f41b 4049
116c20d2 4050 if (pass)
e135f41b 4051 {
116c20d2
NC
4052 /* Pass this symbol through. It is the target of an
4053 indirect or warning symbol. */
4054 val = GET_WORD (input_bfd, sym->e_value);
4055 pass = FALSE;
4056 }
4057 else if (skip_next)
4058 {
4059 /* Skip this symbol, which is the target of an indirect
4060 symbol that we have changed to no longer be an indirect
4061 symbol. */
4062 skip_next = FALSE;
4063 continue;
4064 }
4065 else
4066 {
4067 struct aout_link_hash_entry *hresolve;
e135f41b 4068
116c20d2
NC
4069 /* We have saved the hash table entry for this symbol, if
4070 there is one. Note that we could just look it up again
4071 in the hash table, provided we first check that it is an
4072 external symbol. */
4073 h = *sym_hash;
e135f41b 4074
116c20d2 4075 /* Use the name from the hash table, in case the symbol was
07d6d2b8 4076 wrapped. */
116c20d2
NC
4077 if (h != NULL)
4078 name = h->root.root.string;
e135f41b 4079
116c20d2
NC
4080 /* If this is an indirect or warning symbol, then change
4081 hresolve to the base symbol. We also change *sym_hash so
4082 that the relocation routines relocate against the real
4083 symbol. */
4084 hresolve = h;
4085 if (h != NULL
4086 && (h->root.type == bfd_link_hash_indirect
4087 || h->root.type == bfd_link_hash_warning))
4088 {
4089 hresolve = (struct aout_link_hash_entry *) h->root.u.i.link;
4090 while (hresolve->root.type == bfd_link_hash_indirect
4091 || hresolve->root.type == bfd_link_hash_warning)
4092 hresolve = ((struct aout_link_hash_entry *)
4093 hresolve->root.u.i.link);
4094 *sym_hash = hresolve;
4095 }
e135f41b 4096
116c20d2
NC
4097 /* If the symbol has already been written out, skip it. */
4098 if (h != NULL
4099 && h->root.type != bfd_link_hash_warning
4100 && h->written)
4101 {
4102 if ((type & N_TYPE) == N_INDR
4103 || type == N_WARNING)
4104 skip_next = TRUE;
4105 *symbol_map = h->indx;
4106 continue;
4107 }
e135f41b 4108
116c20d2
NC
4109 /* See if we are stripping this symbol. */
4110 skip = FALSE;
4111 switch (strip)
4112 {
4113 case strip_none:
4114 break;
4115 case strip_debugger:
4116 if ((type & N_STAB) != 0)
4117 skip = TRUE;
4118 break;
4119 case strip_some:
57402f1e 4120 if (bfd_hash_lookup (flaginfo->info->keep_hash, name, FALSE, FALSE)
116c20d2
NC
4121 == NULL)
4122 skip = TRUE;
4123 break;
4124 case strip_all:
4125 skip = TRUE;
4126 break;
e135f41b 4127 }
116c20d2 4128 if (skip)
e135f41b 4129 {
116c20d2
NC
4130 if (h != NULL)
4131 h->written = TRUE;
4132 continue;
4133 }
e135f41b 4134
116c20d2
NC
4135 /* Get the value of the symbol. */
4136 if ((type & N_TYPE) == N_TEXT
4137 || type == N_WEAKT)
4138 symsec = obj_textsec (input_bfd);
4139 else if ((type & N_TYPE) == N_DATA
4140 || type == N_WEAKD)
4141 symsec = obj_datasec (input_bfd);
4142 else if ((type & N_TYPE) == N_BSS
4143 || type == N_WEAKB)
4144 symsec = obj_bsssec (input_bfd);
4145 else if ((type & N_TYPE) == N_ABS
4146 || type == N_WEAKA)
4147 symsec = bfd_abs_section_ptr;
4148 else if (((type & N_TYPE) == N_INDR
4149 && (hresolve == NULL
4150 || (hresolve->root.type != bfd_link_hash_defined
4151 && hresolve->root.type != bfd_link_hash_defweak
4152 && hresolve->root.type != bfd_link_hash_common)))
4153 || type == N_WARNING)
4154 {
4155 /* Pass the next symbol through unchanged. The
4156 condition above for indirect symbols is so that if
4157 the indirect symbol was defined, we output it with
4158 the correct definition so the debugger will
4159 understand it. */
4160 pass = TRUE;
4161 val = GET_WORD (input_bfd, sym->e_value);
4162 symsec = NULL;
4163 }
4164 else if ((type & N_STAB) != 0)
4165 {
4166 val = GET_WORD (input_bfd, sym->e_value);
4167 symsec = NULL;
e135f41b 4168 }
116c20d2
NC
4169 else
4170 {
4171 /* If we get here with an indirect symbol, it means that
4172 we are outputting it with a real definition. In such
4173 a case we do not want to output the next symbol,
4174 which is the target of the indirection. */
4175 if ((type & N_TYPE) == N_INDR)
4176 skip_next = TRUE;
e135f41b 4177
116c20d2 4178 symsec = NULL;
e135f41b 4179
116c20d2
NC
4180 /* We need to get the value from the hash table. We use
4181 hresolve so that if we have defined an indirect
4182 symbol we output the final definition. */
4183 if (h == NULL)
4184 {
4185 switch (type & N_TYPE)
4186 {
4187 case N_SETT:
4188 symsec = obj_textsec (input_bfd);
4189 break;
4190 case N_SETD:
4191 symsec = obj_datasec (input_bfd);
4192 break;
4193 case N_SETB:
4194 symsec = obj_bsssec (input_bfd);
4195 break;
4196 case N_SETA:
4197 symsec = bfd_abs_section_ptr;
4198 break;
4199 default:
4200 val = 0;
4201 break;
4202 }
4203 }
4204 else if (hresolve->root.type == bfd_link_hash_defined
4205 || hresolve->root.type == bfd_link_hash_defweak)
4206 {
4207 asection *input_section;
4208 asection *output_section;
e135f41b 4209
116c20d2
NC
4210 /* This case usually means a common symbol which was
4211 turned into a defined symbol. */
4212 input_section = hresolve->root.u.def.section;
4213 output_section = input_section->output_section;
4214 BFD_ASSERT (bfd_is_abs_section (output_section)
4215 || output_section->owner == output_bfd);
4216 val = (hresolve->root.u.def.value
4217 + bfd_get_section_vma (output_bfd, output_section)
4218 + input_section->output_offset);
e135f41b 4219
116c20d2
NC
4220 /* Get the correct type based on the section. If
4221 this is a constructed set, force it to be
4222 globally visible. */
4223 if (type == N_SETT
4224 || type == N_SETD
4225 || type == N_SETB
4226 || type == N_SETA)
4227 type |= N_EXT;
e135f41b 4228
116c20d2 4229 type &=~ N_TYPE;
e135f41b 4230
116c20d2
NC
4231 if (output_section == obj_textsec (output_bfd))
4232 type |= (hresolve->root.type == bfd_link_hash_defined
4233 ? N_TEXT
4234 : N_WEAKT);
4235 else if (output_section == obj_datasec (output_bfd))
4236 type |= (hresolve->root.type == bfd_link_hash_defined
4237 ? N_DATA
4238 : N_WEAKD);
4239 else if (output_section == obj_bsssec (output_bfd))
4240 type |= (hresolve->root.type == bfd_link_hash_defined
4241 ? N_BSS
4242 : N_WEAKB);
4243 else
4244 type |= (hresolve->root.type == bfd_link_hash_defined
4245 ? N_ABS
4246 : N_WEAKA);
e135f41b 4247 }
116c20d2
NC
4248 else if (hresolve->root.type == bfd_link_hash_common)
4249 val = hresolve->root.u.c.size;
4250 else if (hresolve->root.type == bfd_link_hash_undefweak)
e135f41b 4251 {
116c20d2
NC
4252 val = 0;
4253 type = N_WEAKU;
e135f41b 4254 }
116c20d2
NC
4255 else
4256 val = 0;
e135f41b 4257 }
116c20d2
NC
4258 if (symsec != NULL)
4259 val = (symsec->output_section->vma
4260 + symsec->output_offset
4261 + (GET_WORD (input_bfd, sym->e_value)
4262 - symsec->vma));
e135f41b 4263
116c20d2
NC
4264 /* If this is a global symbol set the written flag, and if
4265 it is a local symbol see if we should discard it. */
4266 if (h != NULL)
e135f41b 4267 {
116c20d2
NC
4268 h->written = TRUE;
4269 h->indx = obj_aout_external_sym_count (output_bfd);
e135f41b 4270 }
116c20d2
NC
4271 else if ((type & N_TYPE) != N_SETT
4272 && (type & N_TYPE) != N_SETD
4273 && (type & N_TYPE) != N_SETB
4274 && (type & N_TYPE) != N_SETA)
e135f41b 4275 {
116c20d2
NC
4276 switch (discard)
4277 {
4278 case discard_none:
4279 case discard_sec_merge:
4280 break;
4281 case discard_l:
4282 if ((type & N_STAB) == 0
4283 && bfd_is_local_label_name (input_bfd, name))
4284 skip = TRUE;
4285 break;
4286 case discard_all:
4287 skip = TRUE;
4288 break;
4289 }
4290 if (skip)
4291 {
4292 pass = FALSE;
4293 continue;
4294 }
e135f41b
NC
4295 }
4296
116c20d2
NC
4297 /* An N_BINCL symbol indicates the start of the stabs
4298 entries for a header file. We need to scan ahead to the
4299 next N_EINCL symbol, ignoring nesting, adding up all the
4300 characters in the symbol names, not including the file
4301 numbers in types (the first number after an open
4302 parenthesis). */
4303 if (type == N_BINCL)
e135f41b 4304 {
116c20d2
NC
4305 struct external_nlist *incl_sym;
4306 int nest;
4307 struct aout_link_includes_entry *incl_entry;
4308 struct aout_link_includes_totals *t;
e135f41b 4309
116c20d2
NC
4310 val = 0;
4311 nest = 0;
4312 for (incl_sym = sym + 1; incl_sym < sym_end; incl_sym++)
4313 {
4314 int incl_type;
e135f41b 4315
116c20d2
NC
4316 incl_type = H_GET_8 (input_bfd, incl_sym->e_type);
4317 if (incl_type == N_EINCL)
4318 {
4319 if (nest == 0)
4320 break;
4321 --nest;
4322 }
4323 else if (incl_type == N_BINCL)
4324 ++nest;
4325 else if (nest == 0)
4326 {
4327 const char *s;
e135f41b 4328
116c20d2
NC
4329 s = strings + GET_WORD (input_bfd, incl_sym->e_strx);
4330 for (; *s != '\0'; s++)
4331 {
4332 val += *s;
4333 if (*s == '(')
4334 {
4335 /* Skip the file number. */
4336 ++s;
4337 while (ISDIGIT (*s))
4338 ++s;
4339 --s;
4340 }
4341 }
4342 }
4343 }
e135f41b 4344
116c20d2 4345 /* If we have already included a header file with the
07d6d2b8
AM
4346 same value, then replace this one with an N_EXCL
4347 symbol. */
57402f1e
NC
4348 copy = ! flaginfo->info->keep_memory;
4349 incl_entry = aout_link_includes_lookup (&flaginfo->includes,
116c20d2
NC
4350 name, TRUE, copy);
4351 if (incl_entry == NULL)
4352 return FALSE;
4353 for (t = incl_entry->totals; t != NULL; t = t->next)
4354 if (t->total == val)
4355 break;
4356 if (t == NULL)
4357 {
4358 /* This is the first time we have seen this header
07d6d2b8 4359 file with this set of stabs strings. */
57402f1e 4360 t = bfd_hash_allocate (&flaginfo->includes.root,
116c20d2
NC
4361 sizeof *t);
4362 if (t == NULL)
4363 return FALSE;
4364 t->total = val;
4365 t->next = incl_entry->totals;
4366 incl_entry->totals = t;
4367 }
4368 else
4369 {
4370 int *incl_map;
e135f41b 4371
116c20d2 4372 /* This is a duplicate header file. We must change
07d6d2b8
AM
4373 it to be an N_EXCL entry, and mark all the
4374 included symbols to prevent outputting them. */
116c20d2 4375 type = N_EXCL;
e135f41b 4376
116c20d2
NC
4377 nest = 0;
4378 for (incl_sym = sym + 1, incl_map = symbol_map + 1;
4379 incl_sym < sym_end;
4380 incl_sym++, incl_map++)
4381 {
4382 int incl_type;
e135f41b 4383
116c20d2
NC
4384 incl_type = H_GET_8 (input_bfd, incl_sym->e_type);
4385 if (incl_type == N_EINCL)
4386 {
4387 if (nest == 0)
4388 {
4389 *incl_map = -1;
4390 break;
4391 }
4392 --nest;
4393 }
4394 else if (incl_type == N_BINCL)
4395 ++nest;
4396 else if (nest == 0)
4397 *incl_map = -1;
4398 }
4399 }
4400 }
e135f41b 4401 }
e135f41b 4402
116c20d2
NC
4403 /* Copy this symbol into the list of symbols we are going to
4404 write out. */
4405 H_PUT_8 (output_bfd, type, outsym->e_type);
4406 copy = FALSE;
57402f1e 4407 if (! flaginfo->info->keep_memory)
e135f41b 4408 {
116c20d2
NC
4409 /* name points into a string table which we are going to
4410 free. If there is a hash table entry, use that string.
4411 Otherwise, copy name into memory. */
4412 if (h != NULL)
4413 name = h->root.root.string;
4414 else
4415 copy = TRUE;
e135f41b 4416 }
57402f1e 4417 strtab_index = add_to_stringtab (output_bfd, flaginfo->strtab,
116c20d2
NC
4418 name, copy);
4419 if (strtab_index == (bfd_size_type) -1)
4420 return FALSE;
4421 PUT_WORD (output_bfd, strtab_index, outsym->e_strx);
4422 PUT_WORD (output_bfd, val, outsym->e_value);
4423 *symbol_map = obj_aout_external_sym_count (output_bfd);
4424 ++obj_aout_external_sym_count (output_bfd);
4425 ++outsym;
e135f41b
NC
4426 }
4427
116c20d2 4428 /* Write out the output symbols we have just constructed. */
57402f1e 4429 if (outsym > flaginfo->output_syms)
e135f41b
NC
4430 {
4431 bfd_size_type size;
e135f41b 4432
57402f1e 4433 if (bfd_seek (output_bfd, flaginfo->symoff, SEEK_SET) != 0)
b34976b6 4434 return FALSE;
57402f1e 4435 size = outsym - flaginfo->output_syms;
116c20d2 4436 size *= EXTERNAL_NLIST_SIZE;
57402f1e 4437 if (bfd_bwrite ((void *) flaginfo->output_syms, size, output_bfd) != size)
b34976b6 4438 return FALSE;
57402f1e 4439 flaginfo->symoff += size;
e135f41b
NC
4440 }
4441
b34976b6 4442 return TRUE;
e135f41b 4443}
116c20d2
NC
4444
4445/* Write out a symbol that was not associated with an a.out input
4446 object. */
e135f41b 4447
edeb6e24
AM
4448static bfd_vma
4449bfd_getp32 (const void *p)
e135f41b 4450{
edeb6e24
AM
4451 const bfd_byte *addr = p;
4452 unsigned long v;
116c20d2 4453
edeb6e24
AM
4454 v = (unsigned long) addr[1] << 24;
4455 v |= (unsigned long) addr[0] << 16;
4456 v |= (unsigned long) addr[3] << 8;
4457 v |= (unsigned long) addr[2];
4458 return v;
e135f41b
NC
4459}
4460
4461#define COERCE32(x) (((bfd_signed_vma) (x) ^ 0x80000000) - 0x80000000)
4462
edeb6e24
AM
4463static bfd_signed_vma
4464bfd_getp_signed_32 (const void *p)
e135f41b 4465{
edeb6e24
AM
4466 const bfd_byte *addr = p;
4467 unsigned long v;
116c20d2 4468
edeb6e24
AM
4469 v = (unsigned long) addr[1] << 24;
4470 v |= (unsigned long) addr[0] << 16;
4471 v |= (unsigned long) addr[3] << 8;
4472 v |= (unsigned long) addr[2];
4473 return COERCE32 (v);
e135f41b
NC
4474}
4475
edeb6e24
AM
4476static void
4477bfd_putp32 (bfd_vma data, void *p)
e135f41b 4478{
edeb6e24 4479 bfd_byte *addr = p;
116c20d2 4480
edeb6e24
AM
4481 addr[0] = (data >> 16) & 0xff;
4482 addr[1] = (data >> 24) & 0xff;
4483 addr[2] = (data >> 0) & 0xff;
4484 addr[3] = (data >> 8) & 0xff;
e135f41b 4485}
116c20d2
NC
4486
4487const bfd_target MY (vec) =
4488{
4489 TARGETNAME, /* Name. */
4490 bfd_target_aout_flavour,
4491 BFD_ENDIAN_LITTLE, /* Target byte order (little). */
4492 BFD_ENDIAN_LITTLE, /* Target headers byte order (little). */
4493 (HAS_RELOC | EXEC_P | /* Object flags. */
4494 HAS_LINENO | HAS_DEBUG |
4495 HAS_SYMS | HAS_LOCALS | WP_TEXT),
4496 (SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_RELOC | SEC_CODE | SEC_DATA),
4497 MY_symbol_leading_char,
4498 AR_PAD_CHAR, /* AR_pad_char. */
4499 15, /* AR_max_namelen. */
0aabe54e 4500 0, /* match priority. */
116c20d2
NC
4501 bfd_getl64, bfd_getl_signed_64, bfd_putl64,
4502 bfd_getp32, bfd_getp_signed_32, bfd_putp32,
4503 bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* Data. */
4504 bfd_getl64, bfd_getl_signed_64, bfd_putl64,
4505 bfd_getp32, bfd_getp_signed_32, bfd_putp32,
4506 bfd_getl16, bfd_getl_signed_16, bfd_putl16, /* Headers. */
d00dd7dc
AM
4507 { /* bfd_check_format. */
4508 _bfd_dummy_target,
4509 MY_object_p,
4510 bfd_generic_archive_p,
4511 MY_core_file_p
4512 },
4513 { /* bfd_set_format. */
4514 _bfd_bool_bfd_false_error,
4515 MY_mkobject,
4516 _bfd_generic_mkarchive,
4517 _bfd_bool_bfd_false_error
4518 },
4519 { /* bfd_write_contents. */
4520 _bfd_bool_bfd_false_error,
4521 MY_write_object_contents,
4522 _bfd_write_archive_contents,
4523 _bfd_bool_bfd_false_error
4524 },
4525
4526 BFD_JUMP_TABLE_GENERIC (MY),
4527 BFD_JUMP_TABLE_COPY (MY),
4528 BFD_JUMP_TABLE_CORE (MY),
4529 BFD_JUMP_TABLE_ARCHIVE (MY),
4530 BFD_JUMP_TABLE_SYMBOLS (MY),
4531 BFD_JUMP_TABLE_RELOCS (MY),
4532 BFD_JUMP_TABLE_WRITE (MY),
4533 BFD_JUMP_TABLE_LINK (MY),
4534 BFD_JUMP_TABLE_DYNAMIC (MY),
116c20d2
NC
4535
4536 /* Alternative_target. */
4537 NULL,
4538
4539 (void *) MY_backend_data
4540};
This page took 1.285042 seconds and 4 git commands to generate.