]> CyberLeo.Net >> Repos - FreeBSD/releng/10.0.git/blob - contrib/binutils/bfd/aoutx.h
- Copy stable/10 (r259064) to releng/10.0 as part of the
[FreeBSD/releng/10.0.git] / contrib / binutils / bfd / aoutx.h
1 /* BFD semi-generic back-end for a.out binaries.
2    Copyright 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
3    2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007
4    Free Software Foundation, Inc.
5    Written by Cygnus Support.
6
7    This file is part of BFD, the Binary File Descriptor library.
8
9    This program is free software; you can redistribute it and/or modify
10    it under the terms of the GNU General Public License as published by
11    the Free Software Foundation; either version 2 of the License, or
12    (at your option) any later version.
13
14    This program is distributed in the hope that it will be useful,
15    but WITHOUT ANY WARRANTY; without even the implied warranty of
16    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17    GNU General Public License for more details.
18
19    You should have received a copy of the GNU General Public License
20    along with this program; if not, write to the Free Software
21    Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA.  */
22
23 /*
24 SECTION
25         a.out backends
26
27 DESCRIPTION
28
29         BFD supports a number of different flavours of a.out format,
30         though the major differences are only the sizes of the
31         structures on disk, and the shape of the relocation
32         information.
33
34         The support is split into a basic support file @file{aoutx.h}
35         and other files which derive functions from the base. One
36         derivation file is @file{aoutf1.h} (for a.out flavour 1), and
37         adds to the basic a.out functions support for sun3, sun4, 386
38         and 29k a.out files, to create a target jump vector for a
39         specific target.
40
41         This information is further split out into more specific files
42         for each machine, including @file{sunos.c} for sun3 and sun4,
43         @file{newsos3.c} for the Sony NEWS, and @file{demo64.c} for a
44         demonstration of a 64 bit a.out format.
45
46         The base file @file{aoutx.h} defines general mechanisms for
47         reading and writing records to and from disk and various
48         other methods which BFD requires. It is included by
49         @file{aout32.c} and @file{aout64.c} to form the names
50         <<aout_32_swap_exec_header_in>>, <<aout_64_swap_exec_header_in>>, etc.
51
52         As an example, this is what goes on to make the back end for a
53         sun4, from @file{aout32.c}:
54
55 |       #define ARCH_SIZE 32
56 |       #include "aoutx.h"
57
58         Which exports names:
59
60 |       ...
61 |       aout_32_canonicalize_reloc
62 |       aout_32_find_nearest_line
63 |       aout_32_get_lineno
64 |       aout_32_get_reloc_upper_bound
65 |       ...
66
67         from @file{sunos.c}:
68
69 |       #define TARGET_NAME "a.out-sunos-big"
70 |       #define VECNAME    sunos_big_vec
71 |       #include "aoutf1.h"
72
73         requires all the names from @file{aout32.c}, and produces the jump vector
74
75 |       sunos_big_vec
76
77         The file @file{host-aout.c} is a special case.  It is for a large set
78         of hosts that use ``more or less standard'' a.out files, and
79         for which cross-debugging is not interesting.  It uses the
80         standard 32-bit a.out support routines, but determines the
81         file offsets and addresses of the text, data, and BSS
82         sections, the machine architecture and machine type, and the
83         entry point address, in a host-dependent manner.  Once these
84         values have been determined, generic code is used to handle
85         the  object file.
86
87         When porting it to run on a new system, you must supply:
88
89 |        HOST_PAGE_SIZE
90 |        HOST_SEGMENT_SIZE
91 |        HOST_MACHINE_ARCH       (optional)
92 |        HOST_MACHINE_MACHINE    (optional)
93 |        HOST_TEXT_START_ADDR
94 |        HOST_STACK_END_ADDR
95
96         in the file @file{../include/sys/h-@var{XXX}.h} (for your host).  These
97         values, plus the structures and macros defined in @file{a.out.h} on
98         your host system, will produce a BFD target that will access
99         ordinary a.out files on your host. To configure a new machine
100         to use @file{host-aout.c}, specify:
101
102 |       TDEFAULTS = -DDEFAULT_VECTOR=host_aout_big_vec
103 |       TDEPFILES= host-aout.o trad-core.o
104
105         in the @file{config/@var{XXX}.mt} file, and modify @file{configure.in}
106         to use the
107         @file{@var{XXX}.mt} file (by setting "<<bfd_target=XXX>>") when your
108         configuration is selected.  */
109
110 /* Some assumptions:
111    * Any BFD with D_PAGED set is ZMAGIC, and vice versa.
112      Doesn't matter what the setting of WP_TEXT is on output, but it'll
113      get set on input.
114    * Any BFD with D_PAGED clear and WP_TEXT set is NMAGIC.
115    * Any BFD with both flags clear is OMAGIC.
116    (Just want to make these explicit, so the conditions tested in this
117    file make sense if you're more familiar with a.out than with BFD.)  */
118
119 #define KEEPIT udata.i
120
121 #include "sysdep.h"
122 #include "bfd.h"
123 #include "safe-ctype.h"
124 #include "bfdlink.h"
125
126 #include "libaout.h"
127 #include "libbfd.h"
128 #include "aout/aout64.h"
129 #include "aout/stab_gnu.h"
130 #include "aout/ar.h"
131
132 /*
133 SUBSECTION
134         Relocations
135
136 DESCRIPTION
137         The file @file{aoutx.h} provides for both the @emph{standard}
138         and @emph{extended} forms of a.out relocation records.
139
140         The standard records contain only an
141         address, a symbol index, and a type field. The extended records
142         (used on 29ks and sparcs) also have a full integer for an
143         addend.  */
144
145 #ifndef CTOR_TABLE_RELOC_HOWTO
146 #define CTOR_TABLE_RELOC_IDX 2
147 #define CTOR_TABLE_RELOC_HOWTO(BFD)                                     \
148   ((obj_reloc_entry_size (BFD) == RELOC_EXT_SIZE                        \
149     ? howto_table_ext : howto_table_std)                                \
150    + CTOR_TABLE_RELOC_IDX)
151 #endif
152
153 #ifndef MY_swap_std_reloc_in
154 #define MY_swap_std_reloc_in NAME (aout, swap_std_reloc_in)
155 #endif
156
157 #ifndef MY_swap_ext_reloc_in
158 #define MY_swap_ext_reloc_in NAME (aout, swap_ext_reloc_in)
159 #endif
160
161 #ifndef MY_swap_std_reloc_out
162 #define MY_swap_std_reloc_out NAME (aout, swap_std_reloc_out)
163 #endif
164
165 #ifndef MY_swap_ext_reloc_out
166 #define MY_swap_ext_reloc_out NAME (aout, swap_ext_reloc_out)
167 #endif
168
169 #ifndef MY_final_link_relocate
170 #define MY_final_link_relocate _bfd_final_link_relocate
171 #endif
172
173 #ifndef MY_relocate_contents
174 #define MY_relocate_contents _bfd_relocate_contents
175 #endif
176
177 #define howto_table_ext NAME (aout, ext_howto_table)
178 #define howto_table_std NAME (aout, std_howto_table)
179
180 reloc_howto_type howto_table_ext[] =
181 {
182   /*     Type         rs   size bsz  pcrel bitpos ovrf                  sf name          part_inpl readmask setmask pcdone.  */
183   HOWTO (RELOC_8,       0,  0,  8,  FALSE, 0, complain_overflow_bitfield, 0, "8",           FALSE, 0, 0x000000ff, FALSE),
184   HOWTO (RELOC_16,      0,  1,  16, FALSE, 0, complain_overflow_bitfield, 0, "16",          FALSE, 0, 0x0000ffff, FALSE),
185   HOWTO (RELOC_32,      0,  2,  32, FALSE, 0, complain_overflow_bitfield, 0, "32",          FALSE, 0, 0xffffffff, FALSE),
186   HOWTO (RELOC_DISP8,   0,  0,  8,  TRUE,  0, complain_overflow_signed,   0, "DISP8",       FALSE, 0, 0x000000ff, FALSE),
187   HOWTO (RELOC_DISP16,  0,  1,  16, TRUE,  0, complain_overflow_signed,   0, "DISP16",      FALSE, 0, 0x0000ffff, FALSE),
188   HOWTO (RELOC_DISP32,  0,  2,  32, TRUE,  0, complain_overflow_signed,   0, "DISP32",      FALSE, 0, 0xffffffff, FALSE),
189   HOWTO (RELOC_WDISP30, 2,  2,  30, TRUE,  0, complain_overflow_signed,   0, "WDISP30",     FALSE, 0, 0x3fffffff, FALSE),
190   HOWTO (RELOC_WDISP22, 2,  2,  22, TRUE,  0, complain_overflow_signed,   0, "WDISP22",     FALSE, 0, 0x003fffff, FALSE),
191   HOWTO (RELOC_HI22,   10,  2,  22, FALSE, 0, complain_overflow_bitfield, 0, "HI22",        FALSE, 0, 0x003fffff, FALSE),
192   HOWTO (RELOC_22,      0,  2,  22, FALSE, 0, complain_overflow_bitfield, 0, "22",          FALSE, 0, 0x003fffff, FALSE),
193   HOWTO (RELOC_13,      0,  2,  13, FALSE, 0, complain_overflow_bitfield, 0, "13",          FALSE, 0, 0x00001fff, FALSE),
194   HOWTO (RELOC_LO10,    0,  2,  10, FALSE, 0, complain_overflow_dont,     0, "LO10",        FALSE, 0, 0x000003ff, FALSE),
195   HOWTO (RELOC_SFA_BASE,0,  2,  32, FALSE, 0, complain_overflow_bitfield, 0, "SFA_BASE",    FALSE, 0, 0xffffffff, FALSE),
196   HOWTO (RELOC_SFA_OFF13,0, 2,  32, FALSE, 0, complain_overflow_bitfield, 0, "SFA_OFF13",   FALSE, 0, 0xffffffff, FALSE),
197   HOWTO (RELOC_BASE10,  0,  2,  10, FALSE, 0, complain_overflow_dont,     0, "BASE10",      FALSE, 0, 0x000003ff, FALSE),
198   HOWTO (RELOC_BASE13,  0,  2,  13, FALSE, 0, complain_overflow_signed,   0, "BASE13",      FALSE, 0, 0x00001fff, FALSE),
199   HOWTO (RELOC_BASE22, 10,  2,  22, FALSE, 0, complain_overflow_bitfield, 0, "BASE22",      FALSE, 0, 0x003fffff, FALSE),
200   HOWTO (RELOC_PC10,    0,  2,  10, TRUE,  0, complain_overflow_dont,     0, "PC10",        FALSE, 0, 0x000003ff, TRUE),
201   HOWTO (RELOC_PC22,   10,  2,  22, TRUE,  0, complain_overflow_signed,   0, "PC22",        FALSE, 0, 0x003fffff, TRUE),
202   HOWTO (RELOC_JMP_TBL, 2,  2,  30, TRUE,  0, complain_overflow_signed,   0, "JMP_TBL",     FALSE, 0, 0x3fffffff, FALSE),
203   HOWTO (RELOC_SEGOFF16,0,  2,  0,  FALSE, 0, complain_overflow_bitfield, 0, "SEGOFF16",    FALSE, 0, 0x00000000, FALSE),
204   HOWTO (RELOC_GLOB_DAT,0,  2,  0,  FALSE, 0, complain_overflow_bitfield, 0, "GLOB_DAT",    FALSE, 0, 0x00000000, FALSE),
205   HOWTO (RELOC_JMP_SLOT,0,  2,  0,  FALSE, 0, complain_overflow_bitfield, 0, "JMP_SLOT",    FALSE, 0, 0x00000000, FALSE),
206   HOWTO (RELOC_RELATIVE,0,  2,  0,  FALSE, 0, complain_overflow_bitfield, 0, "RELATIVE",    FALSE, 0, 0x00000000, FALSE),
207   HOWTO (0,             0,  0,  0,  FALSE, 0, complain_overflow_dont,     0, "R_SPARC_NONE",FALSE, 0, 0x00000000, TRUE),
208   HOWTO (0,             0,  0,  0,  FALSE, 0, complain_overflow_dont,     0, "R_SPARC_NONE",FALSE, 0, 0x00000000, TRUE),
209 #define RELOC_SPARC_REV32 RELOC_WDISP19
210   HOWTO (RELOC_SPARC_REV32, 0, 2, 32, FALSE, 0, complain_overflow_dont,   0,"R_SPARC_REV32",FALSE, 0, 0xffffffff, FALSE),
211 };
212
213 /* Convert standard reloc records to "arelent" format (incl byte swap).  */
214
215 reloc_howto_type howto_table_std[] =
216 {
217   /* type              rs size bsz  pcrel bitpos ovrf                     sf name     part_inpl readmask  setmask    pcdone.  */
218 HOWTO ( 0,             0,  0,   8,  FALSE, 0, complain_overflow_bitfield,0,"8",         TRUE, 0x000000ff,0x000000ff, FALSE),
219 HOWTO ( 1,             0,  1,   16, FALSE, 0, complain_overflow_bitfield,0,"16",        TRUE, 0x0000ffff,0x0000ffff, FALSE),
220 HOWTO ( 2,             0,  2,   32, FALSE, 0, complain_overflow_bitfield,0,"32",        TRUE, 0xffffffff,0xffffffff, FALSE),
221 HOWTO ( 3,             0,  4,   64, FALSE, 0, complain_overflow_bitfield,0,"64",        TRUE, 0xdeaddead,0xdeaddead, FALSE),
222 HOWTO ( 4,             0,  0,   8,  TRUE,  0, complain_overflow_signed,  0,"DISP8",     TRUE, 0x000000ff,0x000000ff, FALSE),
223 HOWTO ( 5,             0,  1,   16, TRUE,  0, complain_overflow_signed,  0,"DISP16",    TRUE, 0x0000ffff,0x0000ffff, FALSE),
224 HOWTO ( 6,             0,  2,   32, TRUE,  0, complain_overflow_signed,  0,"DISP32",    TRUE, 0xffffffff,0xffffffff, FALSE),
225 HOWTO ( 7,             0,  4,   64, TRUE,  0, complain_overflow_signed,  0,"DISP64",    TRUE, 0xfeedface,0xfeedface, FALSE),
226 HOWTO ( 8,             0,  2,    0, FALSE, 0, complain_overflow_bitfield,0,"GOT_REL",   FALSE,         0,0x00000000, FALSE),
227 HOWTO ( 9,             0,  1,   16, FALSE, 0, complain_overflow_bitfield,0,"BASE16",    FALSE,0xffffffff,0xffffffff, FALSE),
228 HOWTO (10,             0,  2,   32, FALSE, 0, complain_overflow_bitfield,0,"BASE32",    FALSE,0xffffffff,0xffffffff, FALSE),
229 EMPTY_HOWTO (-1),
230 EMPTY_HOWTO (-1),
231 EMPTY_HOWTO (-1),
232 EMPTY_HOWTO (-1),
233 EMPTY_HOWTO (-1),
234   HOWTO (16,           0,  2,    0, FALSE, 0, complain_overflow_bitfield,0,"JMP_TABLE", FALSE,         0,0x00000000, FALSE),
235 EMPTY_HOWTO (-1),
236 EMPTY_HOWTO (-1),
237 EMPTY_HOWTO (-1),
238 EMPTY_HOWTO (-1),
239 EMPTY_HOWTO (-1),
240 EMPTY_HOWTO (-1),
241 EMPTY_HOWTO (-1),
242 EMPTY_HOWTO (-1),
243 EMPTY_HOWTO (-1),
244 EMPTY_HOWTO (-1),
245 EMPTY_HOWTO (-1),
246 EMPTY_HOWTO (-1),
247 EMPTY_HOWTO (-1),
248 EMPTY_HOWTO (-1),
249 EMPTY_HOWTO (-1),
250   HOWTO (32,           0,  2,    0, FALSE, 0, complain_overflow_bitfield,0,"RELATIVE",  FALSE,         0,0x00000000, FALSE),
251 EMPTY_HOWTO (-1),
252 EMPTY_HOWTO (-1),
253 EMPTY_HOWTO (-1),
254 EMPTY_HOWTO (-1),
255 EMPTY_HOWTO (-1),
256 EMPTY_HOWTO (-1),
257 EMPTY_HOWTO (-1),
258   HOWTO (40,           0,  2,    0, FALSE, 0, complain_overflow_bitfield,0,"BASEREL",   FALSE,         0,0x00000000, FALSE),
259 };
260
261 #define TABLE_SIZE(TABLE)       (sizeof (TABLE) / sizeof (TABLE[0]))
262
263 reloc_howto_type *
264 NAME (aout, reloc_type_lookup) (bfd *abfd, bfd_reloc_code_real_type code)
265 {
266 #define EXT(i, j)       case i: return & howto_table_ext [j]
267 #define STD(i, j)       case i: return & howto_table_std [j]
268   int ext = obj_reloc_entry_size (abfd) == RELOC_EXT_SIZE;
269
270   if (code == BFD_RELOC_CTOR)
271     switch (bfd_get_arch_info (abfd)->bits_per_address)
272       {
273       case 32:
274         code = BFD_RELOC_32;
275         break;
276       case 64:
277         code = BFD_RELOC_64;
278         break;
279       }
280
281   if (ext)
282     switch (code)
283       {
284         EXT (BFD_RELOC_8, 0);
285         EXT (BFD_RELOC_16, 1);
286         EXT (BFD_RELOC_32, 2);
287         EXT (BFD_RELOC_HI22, 8);
288         EXT (BFD_RELOC_LO10, 11);
289         EXT (BFD_RELOC_32_PCREL_S2, 6);
290         EXT (BFD_RELOC_SPARC_WDISP22, 7);
291         EXT (BFD_RELOC_SPARC13, 10);
292         EXT (BFD_RELOC_SPARC_GOT10, 14);
293         EXT (BFD_RELOC_SPARC_BASE13, 15);
294         EXT (BFD_RELOC_SPARC_GOT13, 15);
295         EXT (BFD_RELOC_SPARC_GOT22, 16);
296         EXT (BFD_RELOC_SPARC_PC10, 17);
297         EXT (BFD_RELOC_SPARC_PC22, 18);
298         EXT (BFD_RELOC_SPARC_WPLT30, 19);
299         EXT (BFD_RELOC_SPARC_REV32, 26);
300       default:
301         return NULL;
302       }
303   else
304     /* std relocs.  */
305     switch (code)
306       {
307         STD (BFD_RELOC_8, 0);
308         STD (BFD_RELOC_16, 1);
309         STD (BFD_RELOC_32, 2);
310         STD (BFD_RELOC_8_PCREL, 4);
311         STD (BFD_RELOC_16_PCREL, 5);
312         STD (BFD_RELOC_32_PCREL, 6);
313         STD (BFD_RELOC_16_BASEREL, 9);
314         STD (BFD_RELOC_32_BASEREL, 10);
315       default:
316         return NULL;
317       }
318 }
319
320 reloc_howto_type *
321 NAME (aout, reloc_name_lookup) (bfd *abfd, const char *r_name)
322 {
323   unsigned int i, size;
324   reloc_howto_type *howto_table;
325
326   if (obj_reloc_entry_size (abfd) == RELOC_EXT_SIZE)
327     {
328       howto_table = howto_table_ext;
329       size = sizeof (howto_table_ext) / sizeof (howto_table_ext[0]);
330     }
331   else
332     {
333       howto_table = howto_table_std;
334       size = sizeof (howto_table_std) / sizeof (howto_table_std[0]);
335     }
336
337   for (i = 0; i < size; i++)
338     if (howto_table[i].name != NULL
339         && strcasecmp (howto_table[i].name, r_name) == 0)
340       return &howto_table[i];
341
342   return NULL;
343 }
344
345 /*
346 SUBSECTION
347         Internal entry points
348
349 DESCRIPTION
350         @file{aoutx.h} exports several routines for accessing the
351         contents of an a.out file, which are gathered and exported in
352         turn by various format specific files (eg sunos.c).
353 */
354
355 /*
356 FUNCTION
357          aout_@var{size}_swap_exec_header_in
358
359 SYNOPSIS
360         void aout_@var{size}_swap_exec_header_in,
361            (bfd *abfd,
362             struct external_exec *bytes,
363             struct internal_exec *execp);
364
365 DESCRIPTION
366         Swap the information in an executable header @var{raw_bytes} taken
367         from a raw byte stream memory image into the internal exec header
368         structure @var{execp}.
369 */
370
371 #ifndef NAME_swap_exec_header_in
372 void
373 NAME (aout, swap_exec_header_in) (bfd *abfd,
374                                   struct external_exec *bytes,
375                                   struct internal_exec *execp)
376 {
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
380      are memcmp'd, and thus the contents do matter.  */
381   memset ((void *) execp, 0, sizeof (struct internal_exec));
382   /* Now fill in fields in the execp, from the bytes in the raw data.  */
383   execp->a_info   = H_GET_32 (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   execp->a_trsize = GET_WORD (abfd, bytes->e_trsize);
390   execp->a_drsize = GET_WORD (abfd, bytes->e_drsize);
391 }
392 #define NAME_swap_exec_header_in NAME (aout, swap_exec_header_in)
393 #endif
394
395 /*
396 FUNCTION
397         aout_@var{size}_swap_exec_header_out
398
399 SYNOPSIS
400         void aout_@var{size}_swap_exec_header_out
401           (bfd *abfd,
402            struct internal_exec *execp,
403            struct external_exec *raw_bytes);
404
405 DESCRIPTION
406         Swap the information in an internal exec header structure
407         @var{execp} into the buffer @var{raw_bytes} ready for writing to disk.
408 */
409 void
410 NAME (aout, swap_exec_header_out) (bfd *abfd,
411                                    struct internal_exec *execp,
412                                    struct external_exec *bytes)
413 {
414   /* Now fill in fields in the raw data, from the fields in the exec struct.  */
415   H_PUT_32 (abfd, execp->a_info  , bytes->e_info);
416   PUT_WORD (abfd, execp->a_text  , bytes->e_text);
417   PUT_WORD (abfd, execp->a_data  , bytes->e_data);
418   PUT_WORD (abfd, execp->a_bss   , bytes->e_bss);
419   PUT_WORD (abfd, execp->a_syms  , bytes->e_syms);
420   PUT_WORD (abfd, execp->a_entry , bytes->e_entry);
421   PUT_WORD (abfd, execp->a_trsize, bytes->e_trsize);
422   PUT_WORD (abfd, execp->a_drsize, bytes->e_drsize);
423 }
424
425 /* Make all the section for an a.out file.  */
426
427 bfd_boolean
428 NAME (aout, make_sections) (bfd *abfd)
429 {
430   if (obj_textsec (abfd) == NULL && bfd_make_section (abfd, ".text") == NULL)
431     return FALSE;
432   if (obj_datasec (abfd) == NULL && bfd_make_section (abfd, ".data") == NULL)
433     return FALSE;
434   if (obj_bsssec (abfd) == NULL && bfd_make_section (abfd, ".bss") == NULL)
435     return FALSE;
436   return TRUE;
437 }
438
439 /*
440 FUNCTION
441         aout_@var{size}_some_aout_object_p
442
443 SYNOPSIS
444         const bfd_target *aout_@var{size}_some_aout_object_p
445          (bfd *abfd,
446           struct internal_exec *execp,
447           const bfd_target *(*callback_to_real_object_p) (bfd *));
448
449 DESCRIPTION
450         Some a.out variant thinks that the file open in @var{abfd}
451         checking is an a.out file.  Do some more checking, and set up
452         for access if it really is.  Call back to the calling
453         environment's "finish up" function just before returning, to
454         handle any last-minute setup.
455 */
456
457 const bfd_target *
458 NAME (aout, some_aout_object_p) (bfd *abfd,
459                                  struct internal_exec *execp,
460                                  const bfd_target *(*callback_to_real_object_p) (bfd *))
461 {
462   struct aout_data_struct *rawptr, *oldrawptr;
463   const bfd_target *result;
464   bfd_size_type amt = sizeof (* rawptr);
465
466   rawptr = bfd_zalloc (abfd, amt);
467   if (rawptr == NULL)
468     return NULL;
469
470   oldrawptr = abfd->tdata.aout_data;
471   abfd->tdata.aout_data = rawptr;
472
473   /* Copy the contents of the old tdata struct.
474      In particular, we want the subformat, since for hpux it was set in
475      hp300hpux.c:swap_exec_header_in and will be used in
476      hp300hpux.c:callback.  */
477   if (oldrawptr != NULL)
478     *abfd->tdata.aout_data = *oldrawptr;
479
480   abfd->tdata.aout_data->a.hdr = &rawptr->e;
481   /* Copy in the internal_exec struct.  */
482   *(abfd->tdata.aout_data->a.hdr) = *execp;
483   execp = abfd->tdata.aout_data->a.hdr;
484
485   /* Set the file flags.  */
486   abfd->flags = BFD_NO_FLAGS;
487   if (execp->a_drsize || execp->a_trsize)
488     abfd->flags |= HAS_RELOC;
489   /* Setting of EXEC_P has been deferred to the bottom of this function.  */
490   if (execp->a_syms)
491     abfd->flags |= HAS_LINENO | HAS_DEBUG | HAS_SYMS | HAS_LOCALS;
492   if (N_DYNAMIC (*execp))
493     abfd->flags |= DYNAMIC;
494
495   if (N_MAGIC (*execp) == ZMAGIC)
496     {
497       abfd->flags |= D_PAGED | WP_TEXT;
498       adata (abfd).magic = z_magic;
499     }
500   else if (N_MAGIC (*execp) == QMAGIC)
501     {
502       abfd->flags |= D_PAGED | WP_TEXT;
503       adata (abfd).magic = z_magic;
504       adata (abfd).subformat = q_magic_format;
505     }
506   else if (N_MAGIC (*execp) == NMAGIC)
507     {
508       abfd->flags |= WP_TEXT;
509       adata (abfd).magic = n_magic;
510     }
511   else if (N_MAGIC (*execp) == OMAGIC
512            || N_MAGIC (*execp) == BMAGIC)
513     adata (abfd).magic = o_magic;
514   else
515     /* Should have been checked with N_BADMAG before this routine
516        was called.  */
517     abort ();
518
519   bfd_get_start_address (abfd) = execp->a_entry;
520
521   obj_aout_symbols (abfd) = NULL;
522   bfd_get_symcount (abfd) = execp->a_syms / sizeof (struct external_nlist);
523
524   /* The default relocation entry size is that of traditional V7 Unix.  */
525   obj_reloc_entry_size (abfd) = RELOC_STD_SIZE;
526
527   /* The default symbol entry size is that of traditional Unix.  */
528   obj_symbol_entry_size (abfd) = EXTERNAL_NLIST_SIZE;
529
530 #ifdef USE_MMAP
531   bfd_init_window (&obj_aout_sym_window (abfd));
532   bfd_init_window (&obj_aout_string_window (abfd));
533 #endif
534   obj_aout_external_syms (abfd) = NULL;
535   obj_aout_external_strings (abfd) = NULL;
536   obj_aout_sym_hashes (abfd) = NULL;
537
538   if (! NAME (aout, make_sections) (abfd))
539     goto error_ret;
540
541   obj_datasec (abfd)->size = execp->a_data;
542   obj_bsssec (abfd)->size = execp->a_bss;
543
544   obj_textsec (abfd)->flags =
545     (execp->a_trsize != 0
546      ? (SEC_ALLOC | SEC_LOAD | SEC_CODE | SEC_HAS_CONTENTS | SEC_RELOC)
547      : (SEC_ALLOC | SEC_LOAD | SEC_CODE | SEC_HAS_CONTENTS));
548   obj_datasec (abfd)->flags =
549     (execp->a_drsize != 0
550      ? (SEC_ALLOC | SEC_LOAD | SEC_DATA | SEC_HAS_CONTENTS | SEC_RELOC)
551      : (SEC_ALLOC | SEC_LOAD | SEC_DATA | SEC_HAS_CONTENTS));
552   obj_bsssec (abfd)->flags = SEC_ALLOC;
553
554 #ifdef THIS_IS_ONLY_DOCUMENTATION
555   /* The common code can't fill in these things because they depend
556      on either the start address of the text segment, the rounding
557      up of virtual addresses between segments, or the starting file
558      position of the text segment -- all of which varies among different
559      versions of a.out.  */
560
561   /* Call back to the format-dependent code to fill in the rest of the
562      fields and do any further cleanup.  Things that should be filled
563      in by the callback:  */
564
565   struct exec *execp = exec_hdr (abfd);
566
567   obj_textsec (abfd)->size = N_TXTSIZE (*execp);
568   /* Data and bss are already filled in since they're so standard.  */
569
570   /* The virtual memory addresses of the sections.  */
571   obj_textsec (abfd)->vma = N_TXTADDR (*execp);
572   obj_datasec (abfd)->vma = N_DATADDR (*execp);
573   obj_bsssec  (abfd)->vma = N_BSSADDR (*execp);
574
575   /* The file offsets of the sections.  */
576   obj_textsec (abfd)->filepos = N_TXTOFF (*execp);
577   obj_datasec (abfd)->filepos = N_DATOFF (*execp);
578
579   /* The file offsets of the relocation info.  */
580   obj_textsec (abfd)->rel_filepos = N_TRELOFF (*execp);
581   obj_datasec (abfd)->rel_filepos = N_DRELOFF (*execp);
582
583   /* The file offsets of the string table and symbol table.  */
584   obj_str_filepos (abfd) = N_STROFF (*execp);
585   obj_sym_filepos (abfd) = N_SYMOFF (*execp);
586
587   /* Determine the architecture and machine type of the object file.  */
588   switch (N_MACHTYPE (*exec_hdr (abfd)))
589     {
590     default:
591       abfd->obj_arch = bfd_arch_obscure;
592       break;
593     }
594
595   adata (abfd)->page_size = TARGET_PAGE_SIZE;
596   adata (abfd)->segment_size = SEGMENT_SIZE;
597   adata (abfd)->exec_bytes_size = EXEC_BYTES_SIZE;
598
599   return abfd->xvec;
600
601   /* The architecture is encoded in various ways in various a.out variants,
602      or is not encoded at all in some of them.  The relocation size depends
603      on the architecture and the a.out variant.  Finally, the return value
604      is the bfd_target vector in use.  If an error occurs, return zero and
605      set bfd_error to the appropriate error code.
606
607      Formats such as b.out, which have additional fields in the a.out
608      header, should cope with them in this callback as well.  */
609 #endif                          /* DOCUMENTATION */
610
611   result = (*callback_to_real_object_p) (abfd);
612
613   /* Now that the segment addresses have been worked out, take a better
614      guess at whether the file is executable.  If the entry point
615      is within the text segment, assume it is.  (This makes files
616      executable even if their entry point address is 0, as long as
617      their text starts at zero.).
618
619      This test had to be changed to deal with systems where the text segment
620      runs at a different location than the default.  The problem is that the
621      entry address can appear to be outside the text segment, thus causing an
622      erroneous conclusion that the file isn't executable.
623
624      To fix this, we now accept any non-zero entry point as an indication of
625      executability.  This will work most of the time, since only the linker
626      sets the entry point, and that is likely to be non-zero for most systems.  */
627
628   if (execp->a_entry != 0
629       || (execp->a_entry >= obj_textsec (abfd)->vma
630           && execp->a_entry < (obj_textsec (abfd)->vma
631                                + obj_textsec (abfd)->size)))
632     abfd->flags |= EXEC_P;
633 #ifdef STAT_FOR_EXEC
634   else
635     {
636       struct stat stat_buf;
637
638       /* The original heuristic doesn't work in some important cases.
639         The a.out file has no information about the text start
640         address.  For files (like kernels) linked to non-standard
641         addresses (ld -Ttext nnn) the entry point may not be between
642         the default text start (obj_textsec(abfd)->vma) and
643         (obj_textsec(abfd)->vma) + text size.  This is not just a mach
644         issue.  Many kernels are loaded at non standard addresses.  */
645       if (abfd->iostream != NULL
646           && (abfd->flags & BFD_IN_MEMORY) == 0
647           && (fstat (fileno ((FILE *) (abfd->iostream)), &stat_buf) == 0)
648           && ((stat_buf.st_mode & 0111) != 0))
649         abfd->flags |= EXEC_P;
650     }
651 #endif /* STAT_FOR_EXEC */
652
653   if (result)
654     return result;
655
656  error_ret:
657   bfd_release (abfd, rawptr);
658   abfd->tdata.aout_data = oldrawptr;
659   return NULL;
660 }
661
662 /*
663 FUNCTION
664         aout_@var{size}_mkobject
665
666 SYNOPSIS
667         bfd_boolean aout_@var{size}_mkobject, (bfd *abfd);
668
669 DESCRIPTION
670         Initialize BFD @var{abfd} for use with a.out files.
671 */
672
673 bfd_boolean
674 NAME (aout, mkobject) (bfd *abfd)
675 {
676   struct aout_data_struct *rawptr;
677   bfd_size_type amt = sizeof (* rawptr);
678
679   bfd_set_error (bfd_error_system_call);
680
681   rawptr = bfd_zalloc (abfd, amt);
682   if (rawptr == NULL)
683     return FALSE;
684
685   abfd->tdata.aout_data = rawptr;
686   exec_hdr (abfd) = &(rawptr->e);
687
688   obj_textsec (abfd) = NULL;
689   obj_datasec (abfd) = NULL;
690   obj_bsssec (abfd) = NULL;
691
692   return TRUE;
693 }
694
695 /*
696 FUNCTION
697         aout_@var{size}_machine_type
698
699 SYNOPSIS
700         enum machine_type  aout_@var{size}_machine_type
701          (enum bfd_architecture arch,
702           unsigned long machine,
703           bfd_boolean *unknown);
704
705 DESCRIPTION
706         Keep track of machine architecture and machine type for
707         a.out's. Return the <<machine_type>> for a particular
708         architecture and machine, or <<M_UNKNOWN>> if that exact architecture
709         and machine can't be represented in a.out format.
710
711         If the architecture is understood, machine type 0 (default)
712         is always understood.
713 */
714
715 enum machine_type
716 NAME (aout, machine_type) (enum bfd_architecture arch,
717                            unsigned long machine,
718                            bfd_boolean *unknown)
719 {
720   enum machine_type arch_flags;
721
722   arch_flags = M_UNKNOWN;
723   *unknown = TRUE;
724
725   switch (arch)
726     {
727     case bfd_arch_sparc:
728       if (machine == 0
729           || machine == bfd_mach_sparc
730           || machine == bfd_mach_sparc_sparclite
731           || machine == bfd_mach_sparc_sparclite_le
732           || machine == bfd_mach_sparc_v8plus
733           || machine == bfd_mach_sparc_v8plusa
734           || machine == bfd_mach_sparc_v8plusb
735           || machine == bfd_mach_sparc_v9
736           || machine == bfd_mach_sparc_v9a
737           || machine == bfd_mach_sparc_v9b)
738         arch_flags = M_SPARC;
739       else if (machine == bfd_mach_sparc_sparclet)
740         arch_flags = M_SPARCLET;
741       break;
742
743     case bfd_arch_m68k:
744       switch (machine)
745         {
746         case 0:               arch_flags = M_68010; break;
747         case bfd_mach_m68000: arch_flags = M_UNKNOWN; *unknown = FALSE; break;
748         case bfd_mach_m68010: arch_flags = M_68010; break;
749         case bfd_mach_m68020: arch_flags = M_68020; break;
750         default:              arch_flags = M_UNKNOWN; break;
751         }
752       break;
753
754     case bfd_arch_i386:
755       if (machine == 0
756           || machine == bfd_mach_i386_i386
757           || machine == bfd_mach_i386_i386_intel_syntax)
758         arch_flags = M_386;
759       break;
760
761     case bfd_arch_arm:
762       if (machine == 0)
763         arch_flags = M_ARM;
764       break;
765
766     case bfd_arch_mips:
767       switch (machine)
768         {
769         case 0:
770         case bfd_mach_mips3000:
771         case bfd_mach_mips3900:
772           arch_flags = M_MIPS1;
773           break;
774         case bfd_mach_mips6000:
775           arch_flags = M_MIPS2;
776           break;
777         case bfd_mach_mips4000:
778         case bfd_mach_mips4010:
779         case bfd_mach_mips4100:
780         case bfd_mach_mips4300:
781         case bfd_mach_mips4400:
782         case bfd_mach_mips4600:
783         case bfd_mach_mips4650:
784         case bfd_mach_mips8000:
785         case bfd_mach_mips9000:
786         case bfd_mach_mips10000:
787         case bfd_mach_mips12000:
788         case bfd_mach_mips16:
789         case bfd_mach_mipsisa32:
790         case bfd_mach_mipsisa32r2:
791         case bfd_mach_mips5:
792         case bfd_mach_mipsisa64:
793         case bfd_mach_mipsisa64r2:
794         case bfd_mach_mips_sb1:
795           /* FIXME: These should be MIPS3, MIPS4, MIPS16, MIPS32, etc.  */
796           arch_flags = M_MIPS2;
797           break;
798         default:
799           arch_flags = M_UNKNOWN;
800           break;
801         }
802       break;
803
804     case bfd_arch_ns32k:
805       switch (machine)
806         {
807         case 0:         arch_flags = M_NS32532; break;
808         case 32032:     arch_flags = M_NS32032; break;
809         case 32532:     arch_flags = M_NS32532; break;
810         default:        arch_flags = M_UNKNOWN; break;
811         }
812       break;
813
814     case bfd_arch_vax:
815       *unknown = FALSE;
816       break;
817
818     case bfd_arch_cris:
819       if (machine == 0 || machine == 255)
820         arch_flags = M_CRIS;
821       break;
822
823     case bfd_arch_m88k:
824       *unknown = FALSE;
825       break;
826
827     default:
828       arch_flags = M_UNKNOWN;
829     }
830
831   if (arch_flags != M_UNKNOWN)
832     *unknown = FALSE;
833
834   return arch_flags;
835 }
836
837 /*
838 FUNCTION
839         aout_@var{size}_set_arch_mach
840
841 SYNOPSIS
842         bfd_boolean aout_@var{size}_set_arch_mach,
843          (bfd *,
844           enum bfd_architecture arch,
845           unsigned long machine);
846
847 DESCRIPTION
848         Set the architecture and the machine of the BFD @var{abfd} to the
849         values @var{arch} and @var{machine}.  Verify that @var{abfd}'s format
850         can support the architecture required.
851 */
852
853 bfd_boolean
854 NAME (aout, set_arch_mach) (bfd *abfd,
855                             enum bfd_architecture arch,
856                             unsigned long machine)
857 {
858   if (! bfd_default_set_arch_mach (abfd, arch, machine))
859     return FALSE;
860
861   if (arch != bfd_arch_unknown)
862     {
863       bfd_boolean unknown;
864
865       NAME (aout, machine_type) (arch, machine, &unknown);
866       if (unknown)
867         return FALSE;
868     }
869
870   /* Determine the size of a relocation entry.  */
871   switch (arch)
872     {
873     case bfd_arch_sparc:
874     case bfd_arch_mips:
875       obj_reloc_entry_size (abfd) = RELOC_EXT_SIZE;
876       break;
877     default:
878       obj_reloc_entry_size (abfd) = RELOC_STD_SIZE;
879       break;
880     }
881
882   return (*aout_backend_info (abfd)->set_sizes) (abfd);
883 }
884
885 static void
886 adjust_o_magic (bfd *abfd, struct internal_exec *execp)
887 {
888   file_ptr pos = adata (abfd).exec_bytes_size;
889   bfd_vma vma = 0;
890   int pad = 0;
891
892   /* Text.  */
893   obj_textsec (abfd)->filepos = pos;
894   if (!obj_textsec (abfd)->user_set_vma)
895     obj_textsec (abfd)->vma = vma;
896   else
897     vma = obj_textsec (abfd)->vma;
898
899   pos += obj_textsec (abfd)->size;
900   vma += obj_textsec (abfd)->size;
901
902   /* Data.  */
903   if (!obj_datasec (abfd)->user_set_vma)
904     {
905       obj_textsec (abfd)->size += pad;
906       pos += pad;
907       vma += pad;
908       obj_datasec (abfd)->vma = vma;
909     }
910   else
911     vma = obj_datasec (abfd)->vma;
912   obj_datasec (abfd)->filepos = pos;
913   pos += obj_datasec (abfd)->size;
914   vma += obj_datasec (abfd)->size;
915
916   /* BSS.  */
917   if (!obj_bsssec (abfd)->user_set_vma)
918     {
919       obj_datasec (abfd)->size += pad;
920       pos += pad;
921       vma += pad;
922       obj_bsssec (abfd)->vma = vma;
923     }
924   else
925     {
926       /* The VMA of the .bss section is set by the VMA of the
927          .data section plus the size of the .data section.  We may
928          need to add padding bytes to make this true.  */
929       pad = obj_bsssec (abfd)->vma - vma;
930       if (pad > 0)
931         {
932           obj_datasec (abfd)->size += pad;
933           pos += pad;
934         }
935     }
936   obj_bsssec (abfd)->filepos = pos;
937
938   /* Fix up the exec header.  */
939   execp->a_text = obj_textsec (abfd)->size;
940   execp->a_data = obj_datasec (abfd)->size;
941   execp->a_bss = obj_bsssec (abfd)->size;
942   N_SET_MAGIC (*execp, OMAGIC);
943 }
944
945 static void
946 adjust_z_magic (bfd *abfd, struct internal_exec *execp)
947 {
948   bfd_size_type data_pad, text_pad;
949   file_ptr text_end;
950   const struct aout_backend_data *abdp;
951   /* TRUE if text includes exec header.  */
952   bfd_boolean ztih;
953
954   abdp = aout_backend_info (abfd);
955
956   /* Text.  */
957   ztih = (abdp != NULL
958           && (abdp->text_includes_header
959               || obj_aout_subformat (abfd) == q_magic_format));
960   obj_textsec (abfd)->filepos = (ztih
961                                  ? adata (abfd).exec_bytes_size
962                                  : adata (abfd).zmagic_disk_block_size);
963   if (! obj_textsec (abfd)->user_set_vma)
964     {
965       /* ?? Do we really need to check for relocs here?  */
966       obj_textsec (abfd)->vma = ((abfd->flags & HAS_RELOC)
967                                  ? 0
968                                  : (ztih
969                                     ? (abdp->default_text_vma
970                                        + adata (abfd).exec_bytes_size)
971                                     : abdp->default_text_vma));
972       text_pad = 0;
973     }
974   else
975     {
976       /* The .text section is being loaded at an unusual address.  We
977          may need to pad it such that the .data section starts at a page
978          boundary.  */
979       if (ztih)
980         text_pad = ((obj_textsec (abfd)->filepos - obj_textsec (abfd)->vma)
981                     & (adata (abfd).page_size - 1));
982       else
983         text_pad = ((- obj_textsec (abfd)->vma)
984                     & (adata (abfd).page_size - 1));
985     }
986
987   /* Find start of data.  */
988   if (ztih)
989     {
990       text_end = obj_textsec (abfd)->filepos + obj_textsec (abfd)->size;
991       text_pad += BFD_ALIGN (text_end, adata (abfd).page_size) - text_end;
992     }
993   else
994     {
995       /* Note that if page_size == zmagic_disk_block_size, then
996          filepos == page_size, and this case is the same as the ztih
997          case.  */
998       text_end = obj_textsec (abfd)->size;
999       text_pad += BFD_ALIGN (text_end, adata (abfd).page_size) - text_end;
1000       text_end += obj_textsec (abfd)->filepos;
1001     }
1002   obj_textsec (abfd)->size += text_pad;
1003   text_end += text_pad;
1004
1005   /* Data.  */
1006   if (!obj_datasec (abfd)->user_set_vma)
1007     {
1008       bfd_vma vma;
1009       vma = obj_textsec (abfd)->vma + obj_textsec (abfd)->size;
1010       obj_datasec (abfd)->vma = BFD_ALIGN (vma, adata (abfd).segment_size);
1011     }
1012   if (abdp && abdp->zmagic_mapped_contiguous)
1013     {
1014       asection * text = obj_textsec (abfd);
1015       asection * data = obj_datasec (abfd);
1016
1017       text_pad = data->vma - (text->vma + text->size);
1018       /* Only pad the text section if the data
1019          section is going to be placed after it.  */
1020       if (text_pad > 0)
1021         text->size += text_pad;
1022     }
1023   obj_datasec (abfd)->filepos = (obj_textsec (abfd)->filepos
1024                                  + obj_textsec (abfd)->size);
1025
1026   /* Fix up exec header while we're at it.  */
1027   execp->a_text = obj_textsec (abfd)->size;
1028   if (ztih && (!abdp || (abdp && !abdp->exec_header_not_counted)))
1029     execp->a_text += adata (abfd).exec_bytes_size;
1030   if (obj_aout_subformat (abfd) == q_magic_format)
1031     N_SET_MAGIC (*execp, QMAGIC);
1032   else
1033     N_SET_MAGIC (*execp, ZMAGIC);
1034
1035   /* Spec says data section should be rounded up to page boundary.  */
1036   obj_datasec (abfd)->size
1037     = align_power (obj_datasec (abfd)->size,
1038                    obj_bsssec (abfd)->alignment_power);
1039   execp->a_data = BFD_ALIGN (obj_datasec (abfd)->size,
1040                              adata (abfd).page_size);
1041   data_pad = execp->a_data - obj_datasec (abfd)->size;
1042
1043   /* BSS.  */
1044   if (!obj_bsssec (abfd)->user_set_vma)
1045     obj_bsssec (abfd)->vma = (obj_datasec (abfd)->vma
1046                               + obj_datasec (abfd)->size);
1047   /* If the BSS immediately follows the data section and extra space
1048      in the page is left after the data section, fudge data
1049      in the header so that the bss section looks smaller by that
1050      amount.  We'll start the bss section there, and lie to the OS.
1051      (Note that a linker script, as well as the above assignment,
1052      could have explicitly set the BSS vma to immediately follow
1053      the data section.)  */
1054   if (align_power (obj_bsssec (abfd)->vma, obj_bsssec (abfd)->alignment_power)
1055       == obj_datasec (abfd)->vma + obj_datasec (abfd)->size)
1056     execp->a_bss = (data_pad > obj_bsssec (abfd)->size
1057                     ? 0 : obj_bsssec (abfd)->size - data_pad);
1058   else
1059     execp->a_bss = obj_bsssec (abfd)->size;
1060 }
1061
1062 static void
1063 adjust_n_magic (bfd *abfd, struct internal_exec *execp)
1064 {
1065   file_ptr pos = adata (abfd).exec_bytes_size;
1066   bfd_vma vma = 0;
1067   int pad;
1068
1069   /* Text.  */
1070   obj_textsec (abfd)->filepos = pos;
1071   if (!obj_textsec (abfd)->user_set_vma)
1072     obj_textsec (abfd)->vma = vma;
1073   else
1074     vma = obj_textsec (abfd)->vma;
1075   pos += obj_textsec (abfd)->size;
1076   vma += obj_textsec (abfd)->size;
1077
1078   /* Data.  */
1079   obj_datasec (abfd)->filepos = pos;
1080   if (!obj_datasec (abfd)->user_set_vma)
1081     obj_datasec (abfd)->vma = BFD_ALIGN (vma, adata (abfd).segment_size);
1082   vma = obj_datasec (abfd)->vma;
1083
1084   /* Since BSS follows data immediately, see if it needs alignment.  */
1085   vma += obj_datasec (abfd)->size;
1086   pad = align_power (vma, obj_bsssec (abfd)->alignment_power) - vma;
1087   obj_datasec (abfd)->size += pad;
1088   pos += obj_datasec (abfd)->size;
1089
1090   /* BSS.  */
1091   if (!obj_bsssec (abfd)->user_set_vma)
1092     obj_bsssec (abfd)->vma = vma;
1093   else
1094     vma = obj_bsssec (abfd)->vma;
1095
1096   /* Fix up exec header.  */
1097   execp->a_text = obj_textsec (abfd)->size;
1098   execp->a_data = obj_datasec (abfd)->size;
1099   execp->a_bss = obj_bsssec (abfd)->size;
1100   N_SET_MAGIC (*execp, NMAGIC);
1101 }
1102
1103 bfd_boolean
1104 NAME (aout, adjust_sizes_and_vmas) (bfd *abfd,
1105                                     bfd_size_type *text_size,
1106                                     file_ptr *text_end ATTRIBUTE_UNUSED)
1107 {
1108   struct internal_exec *execp = exec_hdr (abfd);
1109
1110   if (! NAME (aout, make_sections) (abfd))
1111     return FALSE;
1112
1113   if (adata (abfd).magic != undecided_magic)
1114     return TRUE;
1115
1116   obj_textsec (abfd)->size =
1117     align_power (obj_textsec (abfd)->size,
1118                  obj_textsec (abfd)->alignment_power);
1119
1120   *text_size = obj_textsec (abfd)->size;
1121   /* Rule (heuristic) for when to pad to a new page.  Note that there
1122      are (at least) two ways demand-paged (ZMAGIC) files have been
1123      handled.  Most Berkeley-based systems start the text segment at
1124      (TARGET_PAGE_SIZE).  However, newer versions of SUNOS start the text
1125      segment right after the exec header; the latter is counted in the
1126      text segment size, and is paged in by the kernel with the rest of
1127      the text.  */
1128
1129   /* This perhaps isn't the right way to do this, but made it simpler for me
1130      to understand enough to implement it.  Better would probably be to go
1131      right from BFD flags to alignment/positioning characteristics.  But the
1132      old code was sloppy enough about handling the flags, and had enough
1133      other magic, that it was a little hard for me to understand.  I think
1134      I understand it better now, but I haven't time to do the cleanup this
1135      minute.  */
1136
1137   if (abfd->flags & D_PAGED)
1138     /* Whether or not WP_TEXT is set -- let D_PAGED override.  */
1139     adata (abfd).magic = z_magic;
1140   else if (abfd->flags & WP_TEXT)
1141     adata (abfd).magic = n_magic;
1142   else
1143     adata (abfd).magic = o_magic;
1144
1145 #ifdef BFD_AOUT_DEBUG /* requires gcc2 */
1146 #if __GNUC__ >= 2
1147   fprintf (stderr, "%s text=<%x,%x,%x> data=<%x,%x,%x> bss=<%x,%x,%x>\n",
1148            ({ char *str;
1149               switch (adata (abfd).magic)
1150                 {
1151                 case n_magic: str = "NMAGIC"; break;
1152                 case o_magic: str = "OMAGIC"; break;
1153                 case z_magic: str = "ZMAGIC"; break;
1154                 default: abort ();
1155                 }
1156               str;
1157             }),
1158            obj_textsec (abfd)->vma, obj_textsec (abfd)->size,
1159                 obj_textsec (abfd)->alignment_power,
1160            obj_datasec (abfd)->vma, obj_datasec (abfd)->size,
1161                 obj_datasec (abfd)->alignment_power,
1162            obj_bsssec (abfd)->vma, obj_bsssec (abfd)->size,
1163                 obj_bsssec (abfd)->alignment_power);
1164 #endif
1165 #endif
1166
1167   switch (adata (abfd).magic)
1168     {
1169     case o_magic:
1170       adjust_o_magic (abfd, execp);
1171       break;
1172     case z_magic:
1173       adjust_z_magic (abfd, execp);
1174       break;
1175     case n_magic:
1176       adjust_n_magic (abfd, execp);
1177       break;
1178     default:
1179       abort ();
1180     }
1181
1182 #ifdef BFD_AOUT_DEBUG
1183   fprintf (stderr, "       text=<%x,%x,%x> data=<%x,%x,%x> bss=<%x,%x>\n",
1184            obj_textsec (abfd)->vma, obj_textsec (abfd)->size,
1185                 obj_textsec (abfd)->filepos,
1186            obj_datasec (abfd)->vma, obj_datasec (abfd)->size,
1187                 obj_datasec (abfd)->filepos,
1188            obj_bsssec (abfd)->vma, obj_bsssec (abfd)->size);
1189 #endif
1190
1191   return TRUE;
1192 }
1193
1194 /*
1195 FUNCTION
1196         aout_@var{size}_new_section_hook
1197
1198 SYNOPSIS
1199         bfd_boolean aout_@var{size}_new_section_hook,
1200            (bfd *abfd,
1201             asection *newsect);
1202
1203 DESCRIPTION
1204         Called by the BFD in response to a @code{bfd_make_section}
1205         request.
1206 */
1207 bfd_boolean
1208 NAME (aout, new_section_hook) (bfd *abfd, asection *newsect)
1209 {
1210   /* Align to double at least.  */
1211   newsect->alignment_power = bfd_get_arch_info (abfd)->section_align_power;
1212
1213   if (bfd_get_format (abfd) == bfd_object)
1214     {
1215       if (obj_textsec (abfd) == NULL && !strcmp (newsect->name, ".text"))
1216         {
1217           obj_textsec (abfd)= newsect;
1218           newsect->target_index = N_TEXT;
1219         }
1220       else if (obj_datasec (abfd) == NULL && !strcmp (newsect->name, ".data"))
1221         {
1222           obj_datasec (abfd) = newsect;
1223           newsect->target_index = N_DATA;
1224         }
1225       else if (obj_bsssec (abfd) == NULL && !strcmp (newsect->name, ".bss"))
1226         {
1227           obj_bsssec (abfd) = newsect;
1228           newsect->target_index = N_BSS;
1229         }
1230     }
1231
1232   /* We allow more than three sections internally.  */
1233   return _bfd_generic_new_section_hook (abfd, newsect);
1234 }
1235
1236 bfd_boolean
1237 NAME (aout, set_section_contents) (bfd *abfd,
1238                                    sec_ptr section,
1239                                    const void * location,
1240                                    file_ptr offset,
1241                                    bfd_size_type count)
1242 {
1243   file_ptr text_end;
1244   bfd_size_type text_size;
1245
1246   if (! abfd->output_has_begun)
1247     {
1248       if (! NAME (aout, adjust_sizes_and_vmas) (abfd, &text_size, &text_end))
1249         return FALSE;
1250     }
1251
1252   if (section == obj_bsssec (abfd))
1253     {
1254       bfd_set_error (bfd_error_no_contents);
1255       return FALSE;
1256     }
1257
1258   if (section != obj_textsec (abfd)
1259       && section != obj_datasec (abfd))
1260     {
1261       if (aout_section_merge_with_text_p (abfd, section))
1262         section->filepos = obj_textsec (abfd)->filepos +
1263                            (section->vma - obj_textsec (abfd)->vma);
1264       else
1265         {
1266           (*_bfd_error_handler)
1267            (_("%s: can not represent section `%s' in a.out object file format"),
1268              bfd_get_filename (abfd), bfd_get_section_name (abfd, section));
1269           bfd_set_error (bfd_error_nonrepresentable_section);
1270           return FALSE;
1271         }
1272     }
1273
1274   if (count != 0)
1275     {
1276       if (bfd_seek (abfd, section->filepos + offset, SEEK_SET) != 0
1277           || bfd_bwrite (location, count, abfd) != count)
1278         return FALSE;
1279     }
1280
1281   return TRUE;
1282 }
1283 \f
1284 /* Read the external symbols from an a.out file.  */
1285
1286 static bfd_boolean
1287 aout_get_external_symbols (bfd *abfd)
1288 {
1289   if (obj_aout_external_syms (abfd) == NULL)
1290     {
1291       bfd_size_type count;
1292       struct external_nlist *syms;
1293       bfd_size_type amt;
1294
1295       count = exec_hdr (abfd)->a_syms / EXTERNAL_NLIST_SIZE;
1296
1297 #ifdef USE_MMAP
1298       if (! bfd_get_file_window (abfd, obj_sym_filepos (abfd),
1299                                  exec_hdr (abfd)->a_syms,
1300                                  &obj_aout_sym_window (abfd), TRUE))
1301         return FALSE;
1302       syms = (struct external_nlist *) obj_aout_sym_window (abfd).data;
1303 #else
1304       /* We allocate using malloc to make the values easy to free
1305          later on.  If we put them on the objalloc it might not be
1306          possible to free them.  */
1307       syms = bfd_malloc (count * EXTERNAL_NLIST_SIZE);
1308       if (syms == NULL && count != 0)
1309         return FALSE;
1310
1311       amt = exec_hdr (abfd)->a_syms;
1312       if (bfd_seek (abfd, obj_sym_filepos (abfd), SEEK_SET) != 0
1313           || bfd_bread (syms, amt, abfd) != amt)
1314         {
1315           free (syms);
1316           return FALSE;
1317         }
1318 #endif
1319
1320       obj_aout_external_syms (abfd) = syms;
1321       obj_aout_external_sym_count (abfd) = count;
1322     }
1323
1324   if (obj_aout_external_strings (abfd) == NULL
1325       && exec_hdr (abfd)->a_syms != 0)
1326     {
1327       unsigned char string_chars[BYTES_IN_WORD];
1328       bfd_size_type stringsize;
1329       char *strings;
1330       bfd_size_type amt = BYTES_IN_WORD;
1331
1332       /* Get the size of the strings.  */
1333       if (bfd_seek (abfd, obj_str_filepos (abfd), SEEK_SET) != 0
1334           || bfd_bread ((void *) string_chars, amt, abfd) != amt)
1335         return FALSE;
1336       stringsize = GET_WORD (abfd, string_chars);
1337
1338 #ifdef USE_MMAP
1339       if (! bfd_get_file_window (abfd, obj_str_filepos (abfd), stringsize,
1340                                  &obj_aout_string_window (abfd), TRUE))
1341         return FALSE;
1342       strings = (char *) obj_aout_string_window (abfd).data;
1343 #else
1344       strings = bfd_malloc (stringsize + 1);
1345       if (strings == NULL)
1346         return FALSE;
1347
1348       /* Skip space for the string count in the buffer for convenience
1349          when using indexes.  */
1350       amt = stringsize - BYTES_IN_WORD;
1351       if (bfd_bread (strings + BYTES_IN_WORD, amt, abfd) != amt)
1352         {
1353           free (strings);
1354           return FALSE;
1355         }
1356 #endif
1357
1358       /* Ensure that a zero index yields an empty string.  */
1359       strings[0] = '\0';
1360
1361       strings[stringsize - 1] = 0;
1362
1363       obj_aout_external_strings (abfd) = strings;
1364       obj_aout_external_string_size (abfd) = stringsize;
1365     }
1366
1367   return TRUE;
1368 }
1369
1370 /* Translate an a.out symbol into a BFD symbol.  The desc, other, type
1371    and symbol->value fields of CACHE_PTR will be set from the a.out
1372    nlist structure.  This function is responsible for setting
1373    symbol->flags and symbol->section, and adjusting symbol->value.  */
1374
1375 static bfd_boolean
1376 translate_from_native_sym_flags (bfd *abfd, aout_symbol_type *cache_ptr)
1377 {
1378   flagword visible;
1379
1380   if ((cache_ptr->type & N_STAB) != 0
1381       || cache_ptr->type == N_FN)
1382     {
1383       asection *sec;
1384
1385       /* This is a debugging symbol.  */
1386       cache_ptr->symbol.flags = BSF_DEBUGGING;
1387
1388       /* Work out the symbol section.  */
1389       switch (cache_ptr->type & N_TYPE)
1390         {
1391         case N_TEXT:
1392         case N_FN:
1393           sec = obj_textsec (abfd);
1394           break;
1395         case N_DATA:
1396           sec = obj_datasec (abfd);
1397           break;
1398         case N_BSS:
1399           sec = obj_bsssec (abfd);
1400           break;
1401         default:
1402         case N_ABS:
1403           sec = bfd_abs_section_ptr;
1404           break;
1405         }
1406
1407       cache_ptr->symbol.section = sec;
1408       cache_ptr->symbol.value -= sec->vma;
1409
1410       return TRUE;
1411     }
1412
1413   /* Get the default visibility.  This does not apply to all types, so
1414      we just hold it in a local variable to use if wanted.  */
1415   if ((cache_ptr->type & N_EXT) == 0)
1416     visible = BSF_LOCAL;
1417   else
1418     visible = BSF_GLOBAL;
1419
1420   switch (cache_ptr->type)
1421     {
1422     default:
1423     case N_ABS: case N_ABS | N_EXT:
1424       cache_ptr->symbol.section = bfd_abs_section_ptr;
1425       cache_ptr->symbol.flags = visible;
1426       break;
1427
1428     case N_UNDF | N_EXT:
1429       if (cache_ptr->symbol.value != 0)
1430         {
1431           /* This is a common symbol.  */
1432           cache_ptr->symbol.flags = BSF_GLOBAL;
1433           cache_ptr->symbol.section = bfd_com_section_ptr;
1434         }
1435       else
1436         {
1437           cache_ptr->symbol.flags = 0;
1438           cache_ptr->symbol.section = bfd_und_section_ptr;
1439         }
1440       break;
1441
1442     case N_TEXT: case N_TEXT | N_EXT:
1443       cache_ptr->symbol.section = obj_textsec (abfd);
1444       cache_ptr->symbol.value -= cache_ptr->symbol.section->vma;
1445       cache_ptr->symbol.flags = visible;
1446       break;
1447
1448       /* N_SETV symbols used to represent set vectors placed in the
1449          data section.  They are no longer generated.  Theoretically,
1450          it was possible to extract the entries and combine them with
1451          new ones, although I don't know if that was ever actually
1452          done.  Unless that feature is restored, treat them as data
1453          symbols.  */
1454     case N_SETV: case N_SETV | N_EXT:
1455     case N_DATA: case N_DATA | N_EXT:
1456       cache_ptr->symbol.section = obj_datasec (abfd);
1457       cache_ptr->symbol.value -= cache_ptr->symbol.section->vma;
1458       cache_ptr->symbol.flags = visible;
1459       break;
1460
1461     case N_BSS: case N_BSS | N_EXT:
1462       cache_ptr->symbol.section = obj_bsssec (abfd);
1463       cache_ptr->symbol.value -= cache_ptr->symbol.section->vma;
1464       cache_ptr->symbol.flags = visible;
1465       break;
1466
1467     case N_SETA: case N_SETA | N_EXT:
1468     case N_SETT: case N_SETT | N_EXT:
1469     case N_SETD: case N_SETD | N_EXT:
1470     case N_SETB: case N_SETB | N_EXT:
1471       {
1472         /* This code is no longer needed.  It used to be used to make
1473            the linker handle set symbols, but they are now handled in
1474            the add_symbols routine instead.  */
1475         switch (cache_ptr->type & N_TYPE)
1476           {
1477           case N_SETA:
1478             cache_ptr->symbol.section = bfd_abs_section_ptr;
1479             break;
1480           case N_SETT:
1481             cache_ptr->symbol.section = obj_textsec (abfd);
1482             break;
1483           case N_SETD:
1484             cache_ptr->symbol.section = obj_datasec (abfd);
1485             break;
1486           case N_SETB:
1487             cache_ptr->symbol.section = obj_bsssec (abfd);
1488             break;
1489           }
1490
1491         cache_ptr->symbol.flags |= BSF_CONSTRUCTOR;
1492       }
1493       break;
1494
1495     case N_WARNING:
1496       /* This symbol is the text of a warning message.  The next
1497          symbol is the symbol to associate the warning with.  If a
1498          reference is made to that symbol, a warning is issued.  */
1499       cache_ptr->symbol.flags = BSF_DEBUGGING | BSF_WARNING;
1500       cache_ptr->symbol.section = bfd_abs_section_ptr;
1501       break;
1502
1503     case N_INDR: case N_INDR | N_EXT:
1504       /* An indirect symbol.  This consists of two symbols in a row.
1505          The first symbol is the name of the indirection.  The second
1506          symbol is the name of the target.  A reference to the first
1507          symbol becomes a reference to the second.  */
1508       cache_ptr->symbol.flags = BSF_DEBUGGING | BSF_INDIRECT | visible;
1509       cache_ptr->symbol.section = bfd_ind_section_ptr;
1510       break;
1511
1512     case N_WEAKU:
1513       cache_ptr->symbol.section = bfd_und_section_ptr;
1514       cache_ptr->symbol.flags = BSF_WEAK;
1515       break;
1516
1517     case N_WEAKA:
1518       cache_ptr->symbol.section = bfd_abs_section_ptr;
1519       cache_ptr->symbol.flags = BSF_WEAK;
1520       break;
1521
1522     case N_WEAKT:
1523       cache_ptr->symbol.section = obj_textsec (abfd);
1524       cache_ptr->symbol.value -= cache_ptr->symbol.section->vma;
1525       cache_ptr->symbol.flags = BSF_WEAK;
1526       break;
1527
1528     case N_WEAKD:
1529       cache_ptr->symbol.section = obj_datasec (abfd);
1530       cache_ptr->symbol.value -= cache_ptr->symbol.section->vma;
1531       cache_ptr->symbol.flags = BSF_WEAK;
1532       break;
1533
1534     case N_WEAKB:
1535       cache_ptr->symbol.section = obj_bsssec (abfd);
1536       cache_ptr->symbol.value -= cache_ptr->symbol.section->vma;
1537       cache_ptr->symbol.flags = BSF_WEAK;
1538       break;
1539     }
1540
1541   return TRUE;
1542 }
1543
1544 /* Set the fields of SYM_POINTER according to CACHE_PTR.  */
1545
1546 static bfd_boolean
1547 translate_to_native_sym_flags (bfd *abfd,
1548                                asymbol *cache_ptr,
1549                                struct external_nlist *sym_pointer)
1550 {
1551   bfd_vma value = cache_ptr->value;
1552   asection *sec;
1553   bfd_vma off;
1554
1555   /* Mask out any existing type bits in case copying from one section
1556      to another.  */
1557   sym_pointer->e_type[0] &= ~N_TYPE;
1558
1559   sec = bfd_get_section (cache_ptr);
1560   off = 0;
1561
1562   if (sec == NULL)
1563     {
1564       /* This case occurs, e.g., for the *DEBUG* section of a COFF
1565          file.  */
1566       (*_bfd_error_handler)
1567         (_("%s: can not represent section for symbol `%s' in a.out object file format"),
1568          bfd_get_filename (abfd),
1569          cache_ptr->name != NULL ? cache_ptr->name : _("*unknown*"));
1570       bfd_set_error (bfd_error_nonrepresentable_section);
1571       return FALSE;
1572     }
1573
1574   if (sec->output_section != NULL)
1575     {
1576       off = sec->output_offset;
1577       sec = sec->output_section;
1578     }
1579
1580   if (bfd_is_abs_section (sec))
1581     sym_pointer->e_type[0] |= N_ABS;
1582   else if (sec == obj_textsec (abfd))
1583     sym_pointer->e_type[0] |= N_TEXT;
1584   else if (sec == obj_datasec (abfd))
1585     sym_pointer->e_type[0] |= N_DATA;
1586   else if (sec == obj_bsssec (abfd))
1587     sym_pointer->e_type[0] |= N_BSS;
1588   else if (bfd_is_und_section (sec))
1589     sym_pointer->e_type[0] = N_UNDF | N_EXT;
1590   else if (bfd_is_ind_section (sec))
1591     sym_pointer->e_type[0] = N_INDR;
1592   else if (bfd_is_com_section (sec))
1593     sym_pointer->e_type[0] = N_UNDF | N_EXT;
1594   else
1595     {
1596       if (aout_section_merge_with_text_p (abfd, sec))
1597         sym_pointer->e_type[0] |= N_TEXT;
1598       else
1599         {
1600           (*_bfd_error_handler)
1601            (_("%s: can not represent section `%s' in a.out object file format"),
1602              bfd_get_filename (abfd), bfd_get_section_name (abfd, sec));
1603           bfd_set_error (bfd_error_nonrepresentable_section);
1604           return FALSE;
1605         }
1606     }
1607
1608   /* Turn the symbol from section relative to absolute again.  */
1609   value += sec->vma + off;
1610
1611   if ((cache_ptr->flags & BSF_WARNING) != 0)
1612     sym_pointer->e_type[0] = N_WARNING;
1613
1614   if ((cache_ptr->flags & BSF_DEBUGGING) != 0)
1615     sym_pointer->e_type[0] = ((aout_symbol_type *) cache_ptr)->type;
1616   else if ((cache_ptr->flags & BSF_GLOBAL) != 0)
1617     sym_pointer->e_type[0] |= N_EXT;
1618   else if ((cache_ptr->flags & BSF_LOCAL) != 0)
1619     sym_pointer->e_type[0] &= ~N_EXT;
1620
1621   if ((cache_ptr->flags & BSF_CONSTRUCTOR) != 0)
1622     {
1623       int type = ((aout_symbol_type *) cache_ptr)->type;
1624
1625       switch (type)
1626         {
1627         case N_ABS:     type = N_SETA; break;
1628         case N_TEXT:    type = N_SETT; break;
1629         case N_DATA:    type = N_SETD; break;
1630         case N_BSS:     type = N_SETB; break;
1631         }
1632       sym_pointer->e_type[0] = type;
1633     }
1634
1635   if ((cache_ptr->flags & BSF_WEAK) != 0)
1636     {
1637       int type;
1638
1639       switch (sym_pointer->e_type[0] & N_TYPE)
1640         {
1641         default:
1642         case N_ABS:     type = N_WEAKA; break;
1643         case N_TEXT:    type = N_WEAKT; break;
1644         case N_DATA:    type = N_WEAKD; break;
1645         case N_BSS:     type = N_WEAKB; break;
1646         case N_UNDF:    type = N_WEAKU; break;
1647         }
1648       sym_pointer->e_type[0] = type;
1649     }
1650
1651   PUT_WORD (abfd, value, sym_pointer->e_value);
1652
1653   return TRUE;
1654 }
1655 \f
1656 /* Native-level interface to symbols.  */
1657
1658 asymbol *
1659 NAME (aout, make_empty_symbol) (bfd *abfd)
1660 {
1661   bfd_size_type amt = sizeof (aout_symbol_type);
1662
1663   aout_symbol_type *new = bfd_zalloc (abfd, amt);
1664   if (!new)
1665     return NULL;
1666   new->symbol.the_bfd = abfd;
1667
1668   return &new->symbol;
1669 }
1670
1671 /* Translate a set of internal symbols into external symbols.  */
1672
1673 bfd_boolean
1674 NAME (aout, translate_symbol_table) (bfd *abfd,
1675                                      aout_symbol_type *in,
1676                                      struct external_nlist *ext,
1677                                      bfd_size_type count,
1678                                      char *str,
1679                                      bfd_size_type strsize,
1680                                      bfd_boolean dynamic)
1681 {
1682   struct external_nlist *ext_end;
1683
1684   ext_end = ext + count;
1685   for (; ext < ext_end; ext++, in++)
1686     {
1687       bfd_vma x;
1688
1689       x = GET_WORD (abfd, ext->e_strx);
1690       in->symbol.the_bfd = abfd;
1691
1692       /* For the normal symbols, the zero index points at the number
1693          of bytes in the string table but is to be interpreted as the
1694          null string.  For the dynamic symbols, the number of bytes in
1695          the string table is stored in the __DYNAMIC structure and the
1696          zero index points at an actual string.  */
1697       if (x == 0 && ! dynamic)
1698         in->symbol.name = "";
1699       else if (x < strsize)
1700         in->symbol.name = str + x;
1701       else
1702         return FALSE;
1703
1704       in->symbol.value = GET_SWORD (abfd,  ext->e_value);
1705       in->desc = H_GET_16 (abfd, ext->e_desc);
1706       in->other = H_GET_8 (abfd, ext->e_other);
1707       in->type = H_GET_8 (abfd,  ext->e_type);
1708       in->symbol.udata.p = NULL;
1709
1710       if (! translate_from_native_sym_flags (abfd, in))
1711         return FALSE;
1712
1713       if (dynamic)
1714         in->symbol.flags |= BSF_DYNAMIC;
1715     }
1716
1717   return TRUE;
1718 }
1719
1720 /* We read the symbols into a buffer, which is discarded when this
1721    function exits.  We read the strings into a buffer large enough to
1722    hold them all plus all the cached symbol entries.  */
1723
1724 bfd_boolean
1725 NAME (aout, slurp_symbol_table) (bfd *abfd)
1726 {
1727   struct external_nlist *old_external_syms;
1728   aout_symbol_type *cached;
1729   bfd_size_type cached_size;
1730
1731   /* If there's no work to be done, don't do any.  */
1732   if (obj_aout_symbols (abfd) != NULL)
1733     return TRUE;
1734
1735   old_external_syms = obj_aout_external_syms (abfd);
1736
1737   if (! aout_get_external_symbols (abfd))
1738     return FALSE;
1739
1740   cached_size = obj_aout_external_sym_count (abfd);
1741   cached_size *= sizeof (aout_symbol_type);
1742   cached = bfd_zmalloc (cached_size);
1743   if (cached == NULL && cached_size != 0)
1744     return FALSE;
1745
1746   /* Convert from external symbol information to internal.  */
1747   if (! (NAME (aout, translate_symbol_table)
1748          (abfd, cached,
1749           obj_aout_external_syms (abfd),
1750           obj_aout_external_sym_count (abfd),
1751           obj_aout_external_strings (abfd),
1752           obj_aout_external_string_size (abfd),
1753           FALSE)))
1754     {
1755       free (cached);
1756       return FALSE;
1757     }
1758
1759   bfd_get_symcount (abfd) = obj_aout_external_sym_count (abfd);
1760
1761   obj_aout_symbols (abfd) = cached;
1762
1763   /* It is very likely that anybody who calls this function will not
1764      want the external symbol information, so if it was allocated
1765      because of our call to aout_get_external_symbols, we free it up
1766      right away to save space.  */
1767   if (old_external_syms == NULL
1768       && obj_aout_external_syms (abfd) != NULL)
1769     {
1770 #ifdef USE_MMAP
1771       bfd_free_window (&obj_aout_sym_window (abfd));
1772 #else
1773       free (obj_aout_external_syms (abfd));
1774 #endif
1775       obj_aout_external_syms (abfd) = NULL;
1776     }
1777
1778   return TRUE;
1779 }
1780 \f
1781 /* We use a hash table when writing out symbols so that we only write
1782    out a particular string once.  This helps particularly when the
1783    linker writes out stabs debugging entries, because each different
1784    contributing object file tends to have many duplicate stabs
1785    strings.
1786
1787    This hash table code breaks dbx on SunOS 4.1.3, so we don't do it
1788    if BFD_TRADITIONAL_FORMAT is set.  */
1789
1790 /* Get the index of a string in a strtab, adding it if it is not
1791    already present.  */
1792
1793 static inline bfd_size_type
1794 add_to_stringtab (bfd *abfd,
1795                   struct bfd_strtab_hash *tab,
1796                   const char *str,
1797                   bfd_boolean copy)
1798 {
1799   bfd_boolean hash;
1800   bfd_size_type index;
1801
1802   /* An index of 0 always means the empty string.  */
1803   if (str == 0 || *str == '\0')
1804     return 0;
1805
1806   /* Don't hash if BFD_TRADITIONAL_FORMAT is set, because SunOS dbx
1807      doesn't understand a hashed string table.  */
1808   hash = TRUE;
1809   if ((abfd->flags & BFD_TRADITIONAL_FORMAT) != 0)
1810     hash = FALSE;
1811
1812   index = _bfd_stringtab_add (tab, str, hash, copy);
1813
1814   if (index != (bfd_size_type) -1)
1815     /* Add BYTES_IN_WORD to the return value to account for the
1816        space taken up by the string table size.  */
1817     index += BYTES_IN_WORD;
1818
1819   return index;
1820 }
1821
1822 /* Write out a strtab.  ABFD is already at the right location in the
1823    file.  */
1824
1825 static bfd_boolean
1826 emit_stringtab (bfd *abfd, struct bfd_strtab_hash *tab)
1827 {
1828   bfd_byte buffer[BYTES_IN_WORD];
1829   bfd_size_type amt = BYTES_IN_WORD;
1830
1831   /* The string table starts with the size.  */
1832   PUT_WORD (abfd, _bfd_stringtab_size (tab) + BYTES_IN_WORD, buffer);
1833   if (bfd_bwrite ((void *) buffer, amt, abfd) != amt)
1834     return FALSE;
1835
1836   return _bfd_stringtab_emit (abfd, tab);
1837 }
1838 \f
1839 bfd_boolean
1840 NAME (aout, write_syms) (bfd *abfd)
1841 {
1842   unsigned int count ;
1843   asymbol **generic = bfd_get_outsymbols (abfd);
1844   struct bfd_strtab_hash *strtab;
1845
1846   strtab = _bfd_stringtab_init ();
1847   if (strtab == NULL)
1848     return FALSE;
1849
1850   for (count = 0; count < bfd_get_symcount (abfd); count++)
1851     {
1852       asymbol *g = generic[count];
1853       bfd_size_type indx;
1854       struct external_nlist nsp;
1855       bfd_size_type amt;
1856
1857       indx = add_to_stringtab (abfd, strtab, g->name, FALSE);
1858       if (indx == (bfd_size_type) -1)
1859         goto error_return;
1860       PUT_WORD (abfd, indx, (bfd_byte *) nsp.e_strx);
1861
1862       if (bfd_asymbol_flavour (g) == abfd->xvec->flavour)
1863         {
1864           H_PUT_16 (abfd, aout_symbol (g)->desc,  nsp.e_desc);
1865           H_PUT_8  (abfd, aout_symbol (g)->other, nsp.e_other);
1866           H_PUT_8  (abfd, aout_symbol (g)->type,  nsp.e_type);
1867         }
1868       else
1869         {
1870           H_PUT_16 (abfd, 0, nsp.e_desc);
1871           H_PUT_8  (abfd, 0, nsp.e_other);
1872           H_PUT_8  (abfd, 0, nsp.e_type);
1873         }
1874
1875       if (! translate_to_native_sym_flags (abfd, g, &nsp))
1876         goto error_return;
1877
1878       amt = EXTERNAL_NLIST_SIZE;
1879       if (bfd_bwrite ((void *) &nsp, amt, abfd) != amt)
1880         goto error_return;
1881
1882       /* NB: `KEEPIT' currently overlays `udata.p', so set this only
1883          here, at the end.  */
1884       g->KEEPIT = count;
1885     }
1886
1887   if (! emit_stringtab (abfd, strtab))
1888     goto error_return;
1889
1890   _bfd_stringtab_free (strtab);
1891
1892   return TRUE;
1893
1894 error_return:
1895   _bfd_stringtab_free (strtab);
1896   return FALSE;
1897 }
1898 \f
1899 long
1900 NAME (aout, canonicalize_symtab) (bfd *abfd, asymbol **location)
1901 {
1902   unsigned int counter = 0;
1903   aout_symbol_type *symbase;
1904
1905   if (!NAME (aout, slurp_symbol_table) (abfd))
1906     return -1;
1907
1908   for (symbase = obj_aout_symbols (abfd);
1909        counter++ < bfd_get_symcount (abfd);
1910        )
1911     *(location++) = (asymbol *) (symbase++);
1912   *location++ =0;
1913   return bfd_get_symcount (abfd);
1914 }
1915 \f
1916 /* Standard reloc stuff.  */
1917 /* Output standard relocation information to a file in target byte order.  */
1918
1919 extern void  NAME (aout, swap_std_reloc_out)
1920   (bfd *, arelent *, struct reloc_std_external *);
1921
1922 void
1923 NAME (aout, swap_std_reloc_out) (bfd *abfd,
1924                                  arelent *g,
1925                                  struct reloc_std_external *natptr)
1926 {
1927   int r_index;
1928   asymbol *sym = *(g->sym_ptr_ptr);
1929   int r_extern;
1930   unsigned int r_length;
1931   int r_pcrel;
1932   int r_baserel, r_jmptable, r_relative;
1933   asection *output_section = sym->section->output_section;
1934
1935   PUT_WORD (abfd, g->address, natptr->r_address);
1936
1937   r_length = g->howto->size ;   /* Size as a power of two.  */
1938   r_pcrel  = (int) g->howto->pc_relative; /* Relative to PC?  */
1939   /* XXX This relies on relocs coming from a.out files.  */
1940   r_baserel = (g->howto->type & 8) != 0;
1941   r_jmptable = (g->howto->type & 16) != 0;
1942   r_relative = (g->howto->type & 32) != 0;
1943
1944   /* Name was clobbered by aout_write_syms to be symbol index.  */
1945
1946   /* If this relocation is relative to a symbol then set the
1947      r_index to the symbols index, and the r_extern bit.
1948
1949      Absolute symbols can come in in two ways, either as an offset
1950      from the abs section, or as a symbol which has an abs value.
1951      check for that here.  */
1952
1953   if (bfd_is_com_section (output_section)
1954       || bfd_is_abs_section (output_section)
1955       || bfd_is_und_section (output_section)
1956       /* PR gas/3041  a.out relocs against weak symbols
1957          must be treated as if they were against externs.  */
1958       || (sym->flags & BSF_WEAK))
1959     {
1960       if (bfd_abs_section_ptr->symbol == sym)
1961         {
1962           /* Whoops, looked like an abs symbol, but is
1963              really an offset from the abs section.  */
1964           r_index = N_ABS;
1965           r_extern = 0;
1966         }
1967       else
1968         {
1969           /* Fill in symbol.  */
1970           r_extern = 1;
1971           r_index = (*(g->sym_ptr_ptr))->KEEPIT;
1972         }
1973     }
1974   else
1975     {
1976       /* Just an ordinary section.  */
1977       r_extern = 0;
1978       r_index  = output_section->target_index;
1979     }
1980
1981   /* Now the fun stuff.  */
1982   if (bfd_header_big_endian (abfd))
1983     {
1984       natptr->r_index[0] = r_index >> 16;
1985       natptr->r_index[1] = r_index >> 8;
1986       natptr->r_index[2] = r_index;
1987       natptr->r_type[0] = ((r_extern ? RELOC_STD_BITS_EXTERN_BIG : 0)
1988                            | (r_pcrel ? RELOC_STD_BITS_PCREL_BIG : 0)
1989                            | (r_baserel ? RELOC_STD_BITS_BASEREL_BIG : 0)
1990                            | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_BIG : 0)
1991                            | (r_relative ? RELOC_STD_BITS_RELATIVE_BIG : 0)
1992                            | (r_length << RELOC_STD_BITS_LENGTH_SH_BIG));
1993     }
1994   else
1995     {
1996       natptr->r_index[2] = r_index >> 16;
1997       natptr->r_index[1] = r_index >> 8;
1998       natptr->r_index[0] = r_index;
1999       natptr->r_type[0] = ((r_extern ? RELOC_STD_BITS_EXTERN_LITTLE : 0)
2000                            | (r_pcrel ? RELOC_STD_BITS_PCREL_LITTLE : 0)
2001                            | (r_baserel ? RELOC_STD_BITS_BASEREL_LITTLE : 0)
2002                            | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_LITTLE : 0)
2003                            | (r_relative ? RELOC_STD_BITS_RELATIVE_LITTLE : 0)
2004                            | (r_length << RELOC_STD_BITS_LENGTH_SH_LITTLE));
2005     }
2006 }
2007
2008 /* Extended stuff.  */
2009 /* Output extended relocation information to a file in target byte order.  */
2010
2011 extern void NAME (aout, swap_ext_reloc_out)
2012   (bfd *, arelent *, struct reloc_ext_external *);
2013
2014 void
2015 NAME (aout, swap_ext_reloc_out) (bfd *abfd,
2016                                  arelent *g,
2017                                  struct reloc_ext_external *natptr)
2018 {
2019   int r_index;
2020   int r_extern;
2021   unsigned int r_type;
2022   bfd_vma r_addend;
2023   asymbol *sym = *(g->sym_ptr_ptr);
2024   asection *output_section = sym->section->output_section;
2025
2026   PUT_WORD (abfd, g->address, natptr->r_address);
2027
2028   r_type = (unsigned int) g->howto->type;
2029
2030   r_addend = g->addend;
2031   if ((sym->flags & BSF_SECTION_SYM) != 0)
2032     r_addend += (*(g->sym_ptr_ptr))->section->output_section->vma;
2033
2034   /* If this relocation is relative to a symbol then set the
2035      r_index to the symbols index, and the r_extern bit.
2036
2037      Absolute symbols can come in in two ways, either as an offset
2038      from the abs section, or as a symbol which has an abs value.
2039      check for that here.  */
2040   if (bfd_is_abs_section (bfd_get_section (sym)))
2041     {
2042       r_extern = 0;
2043       r_index = N_ABS;
2044     }
2045   else if ((sym->flags & BSF_SECTION_SYM) == 0)
2046     {
2047       if (bfd_is_und_section (bfd_get_section (sym))
2048           || (sym->flags & BSF_GLOBAL) != 0)
2049         r_extern = 1;
2050       else
2051         r_extern = 0;
2052       r_index = (*(g->sym_ptr_ptr))->KEEPIT;
2053     }
2054   else
2055     {
2056       /* Just an ordinary section.  */
2057       r_extern = 0;
2058       r_index = output_section->target_index;
2059     }
2060
2061   /* Now the fun stuff.  */
2062   if (bfd_header_big_endian (abfd))
2063     {
2064       natptr->r_index[0] = r_index >> 16;
2065       natptr->r_index[1] = r_index >> 8;
2066       natptr->r_index[2] = r_index;
2067       natptr->r_type[0] = ((r_extern ? RELOC_EXT_BITS_EXTERN_BIG : 0)
2068                            | (r_type << RELOC_EXT_BITS_TYPE_SH_BIG));
2069     }
2070   else
2071     {
2072       natptr->r_index[2] = r_index >> 16;
2073       natptr->r_index[1] = r_index >> 8;
2074       natptr->r_index[0] = r_index;
2075       natptr->r_type[0] = ((r_extern ? RELOC_EXT_BITS_EXTERN_LITTLE : 0)
2076                            | (r_type << RELOC_EXT_BITS_TYPE_SH_LITTLE));
2077     }
2078
2079   PUT_WORD (abfd, r_addend, natptr->r_addend);
2080 }
2081
2082 /* BFD deals internally with all things based from the section they're
2083    in. so, something in 10 bytes into a text section  with a base of
2084    50 would have a symbol (.text+10) and know .text vma was 50.
2085
2086    Aout keeps all it's symbols based from zero, so the symbol would
2087    contain 60. This macro subs the base of each section from the value
2088    to give the true offset from the section.  */
2089
2090 #define MOVE_ADDRESS(ad)                                                \
2091   if (r_extern)                                                         \
2092     {                                                                   \
2093       /* Undefined symbol.  */                                          \
2094       cache_ptr->sym_ptr_ptr = symbols + r_index;                       \
2095       cache_ptr->addend = ad;                                           \
2096     }                                                                   \
2097    else                                                                 \
2098     {                                                                   \
2099       /* Defined, section relative.  Replace symbol with pointer to     \
2100          symbol which points to section.  */                            \
2101       switch (r_index)                                                  \
2102         {                                                               \
2103         case N_TEXT:                                                    \
2104         case N_TEXT | N_EXT:                                            \
2105           cache_ptr->sym_ptr_ptr = obj_textsec (abfd)->symbol_ptr_ptr;  \
2106           cache_ptr->addend = ad - su->textsec->vma;                    \
2107           break;                                                        \
2108         case N_DATA:                                                    \
2109         case N_DATA | N_EXT:                                            \
2110           cache_ptr->sym_ptr_ptr = obj_datasec (abfd)->symbol_ptr_ptr;  \
2111           cache_ptr->addend = ad - su->datasec->vma;                    \
2112           break;                                                        \
2113         case N_BSS:                                                     \
2114         case N_BSS | N_EXT:                                             \
2115           cache_ptr->sym_ptr_ptr = obj_bsssec (abfd)->symbol_ptr_ptr;   \
2116           cache_ptr->addend = ad - su->bsssec->vma;                     \
2117           break;                                                        \
2118         default:                                                        \
2119         case N_ABS:                                                     \
2120         case N_ABS | N_EXT:                                             \
2121           cache_ptr->sym_ptr_ptr = bfd_abs_section_ptr->symbol_ptr_ptr; \
2122           cache_ptr->addend = ad;                                       \
2123           break;                                                        \
2124         }                                                               \
2125     }
2126
2127 void
2128 NAME (aout, swap_ext_reloc_in) (bfd *abfd,
2129                                 struct reloc_ext_external *bytes,
2130                                 arelent *cache_ptr,
2131                                 asymbol **symbols,
2132                                 bfd_size_type symcount)
2133 {
2134   unsigned int r_index;
2135   int r_extern;
2136   unsigned int r_type;
2137   struct aoutdata *su = &(abfd->tdata.aout_data->a);
2138
2139   cache_ptr->address = (GET_SWORD (abfd, bytes->r_address));
2140
2141   /* Now the fun stuff.  */
2142   if (bfd_header_big_endian (abfd))
2143     {
2144       r_index = (((unsigned int) bytes->r_index[0] << 16)
2145                  | ((unsigned int) bytes->r_index[1] << 8)
2146                  | bytes->r_index[2]);
2147       r_extern = (0 != (bytes->r_type[0] & RELOC_EXT_BITS_EXTERN_BIG));
2148       r_type = ((bytes->r_type[0] & RELOC_EXT_BITS_TYPE_BIG)
2149                 >> RELOC_EXT_BITS_TYPE_SH_BIG);
2150     }
2151   else
2152     {
2153       r_index =  (((unsigned int) bytes->r_index[2] << 16)
2154                   | ((unsigned int) bytes->r_index[1] << 8)
2155                   | bytes->r_index[0]);
2156       r_extern = (0 != (bytes->r_type[0] & RELOC_EXT_BITS_EXTERN_LITTLE));
2157       r_type = ((bytes->r_type[0] & RELOC_EXT_BITS_TYPE_LITTLE)
2158                 >> RELOC_EXT_BITS_TYPE_SH_LITTLE);
2159     }
2160
2161   cache_ptr->howto =  howto_table_ext + r_type;
2162
2163   /* Base relative relocs are always against the symbol table,
2164      regardless of the setting of r_extern.  r_extern just reflects
2165      whether the symbol the reloc is against is local or global.  */
2166   if (r_type == (unsigned int) RELOC_BASE10
2167       || r_type == (unsigned int) RELOC_BASE13
2168       || r_type == (unsigned int) RELOC_BASE22)
2169     r_extern = 1;
2170
2171   if (r_extern && r_index > symcount)
2172     {
2173       /* We could arrange to return an error, but it might be useful
2174          to see the file even if it is bad.  */
2175       r_extern = 0;
2176       r_index = N_ABS;
2177     }
2178
2179   MOVE_ADDRESS (GET_SWORD (abfd, bytes->r_addend));
2180 }
2181
2182 void
2183 NAME (aout, swap_std_reloc_in) (bfd *abfd,
2184                                 struct reloc_std_external *bytes,
2185                                 arelent *cache_ptr,
2186                                 asymbol **symbols,
2187                                 bfd_size_type symcount)
2188 {
2189   unsigned int r_index;
2190   int r_extern;
2191   unsigned int r_length;
2192   int r_pcrel;
2193   int r_baserel, r_jmptable, r_relative;
2194   struct aoutdata  *su = &(abfd->tdata.aout_data->a);
2195   unsigned int howto_idx;
2196
2197   cache_ptr->address = H_GET_32 (abfd, bytes->r_address);
2198
2199   /* Now the fun stuff.  */
2200   if (bfd_header_big_endian (abfd))
2201     {
2202       r_index = (((unsigned int) bytes->r_index[0] << 16)
2203                  | ((unsigned int) bytes->r_index[1] << 8)
2204                  | bytes->r_index[2]);
2205       r_extern  = (0 != (bytes->r_type[0] & RELOC_STD_BITS_EXTERN_BIG));
2206       r_pcrel   = (0 != (bytes->r_type[0] & RELOC_STD_BITS_PCREL_BIG));
2207       r_baserel = (0 != (bytes->r_type[0] & RELOC_STD_BITS_BASEREL_BIG));
2208       r_jmptable= (0 != (bytes->r_type[0] & RELOC_STD_BITS_JMPTABLE_BIG));
2209       r_relative= (0 != (bytes->r_type[0] & RELOC_STD_BITS_RELATIVE_BIG));
2210       r_length  = ((bytes->r_type[0] & RELOC_STD_BITS_LENGTH_BIG)
2211                    >> RELOC_STD_BITS_LENGTH_SH_BIG);
2212     }
2213   else
2214     {
2215       r_index = (((unsigned int) bytes->r_index[2] << 16)
2216                  | ((unsigned int) bytes->r_index[1] << 8)
2217                  | bytes->r_index[0]);
2218       r_extern  = (0 != (bytes->r_type[0] & RELOC_STD_BITS_EXTERN_LITTLE));
2219       r_pcrel   = (0 != (bytes->r_type[0] & RELOC_STD_BITS_PCREL_LITTLE));
2220       r_baserel = (0 != (bytes->r_type[0] & RELOC_STD_BITS_BASEREL_LITTLE));
2221       r_jmptable= (0 != (bytes->r_type[0] & RELOC_STD_BITS_JMPTABLE_LITTLE));
2222       r_relative= (0 != (bytes->r_type[0] & RELOC_STD_BITS_RELATIVE_LITTLE));
2223       r_length  = ((bytes->r_type[0] & RELOC_STD_BITS_LENGTH_LITTLE)
2224                    >> RELOC_STD_BITS_LENGTH_SH_LITTLE);
2225     }
2226
2227   howto_idx = (r_length + 4 * r_pcrel + 8 * r_baserel
2228                + 16 * r_jmptable + 32 * r_relative);
2229   BFD_ASSERT (howto_idx < TABLE_SIZE (howto_table_std));
2230   cache_ptr->howto =  howto_table_std + howto_idx;
2231   BFD_ASSERT (cache_ptr->howto->type != (unsigned int) -1);
2232
2233   /* Base relative relocs are always against the symbol table,
2234      regardless of the setting of r_extern.  r_extern just reflects
2235      whether the symbol the reloc is against is local or global.  */
2236   if (r_baserel)
2237     r_extern = 1;
2238
2239   if (r_extern && r_index > symcount)
2240     {
2241       /* We could arrange to return an error, but it might be useful
2242          to see the file even if it is bad.  */
2243       r_extern = 0;
2244       r_index = N_ABS;
2245     }
2246
2247   MOVE_ADDRESS (0);
2248 }
2249
2250 /* Read and swap the relocs for a section.  */
2251
2252 bfd_boolean
2253 NAME (aout, slurp_reloc_table) (bfd *abfd, sec_ptr asect, asymbol **symbols)
2254 {
2255   bfd_size_type count;
2256   bfd_size_type reloc_size;
2257   void * relocs;
2258   arelent *reloc_cache;
2259   size_t each_size;
2260   unsigned int counter = 0;
2261   arelent *cache_ptr;
2262   bfd_size_type amt;
2263
2264   if (asect->relocation)
2265     return TRUE;
2266
2267   if (asect->flags & SEC_CONSTRUCTOR)
2268     return TRUE;
2269
2270   if (asect == obj_datasec (abfd))
2271     reloc_size = exec_hdr (abfd)->a_drsize;
2272   else if (asect == obj_textsec (abfd))
2273     reloc_size = exec_hdr (abfd)->a_trsize;
2274   else if (asect == obj_bsssec (abfd))
2275     reloc_size = 0;
2276   else
2277     {
2278       bfd_set_error (bfd_error_invalid_operation);
2279       return FALSE;
2280     }
2281
2282   if (bfd_seek (abfd, asect->rel_filepos, SEEK_SET) != 0)
2283     return FALSE;
2284
2285   each_size = obj_reloc_entry_size (abfd);
2286
2287   count = reloc_size / each_size;
2288
2289   amt = count * sizeof (arelent);
2290   reloc_cache = bfd_zmalloc (amt);
2291   if (reloc_cache == NULL && count != 0)
2292     return FALSE;
2293
2294   relocs = bfd_malloc (reloc_size);
2295   if (relocs == NULL && reloc_size != 0)
2296     {
2297       free (reloc_cache);
2298       return FALSE;
2299     }
2300
2301   if (bfd_bread (relocs, reloc_size, abfd) != reloc_size)
2302     {
2303       free (relocs);
2304       free (reloc_cache);
2305       return FALSE;
2306     }
2307
2308   cache_ptr = reloc_cache;
2309   if (each_size == RELOC_EXT_SIZE)
2310     {
2311       struct reloc_ext_external *rptr = (struct reloc_ext_external *) relocs;
2312
2313       for (; counter < count; counter++, rptr++, cache_ptr++)
2314         MY_swap_ext_reloc_in (abfd, rptr, cache_ptr, symbols,
2315                               (bfd_size_type) bfd_get_symcount (abfd));
2316     }
2317   else
2318     {
2319       struct reloc_std_external *rptr = (struct reloc_std_external *) relocs;
2320
2321       for (; counter < count; counter++, rptr++, cache_ptr++)
2322         MY_swap_std_reloc_in (abfd, rptr, cache_ptr, symbols,
2323                               (bfd_size_type) bfd_get_symcount (abfd));
2324     }
2325
2326   free (relocs);
2327
2328   asect->relocation = reloc_cache;
2329   asect->reloc_count = cache_ptr - reloc_cache;
2330
2331   return TRUE;
2332 }
2333
2334 /* Write out a relocation section into an object file.  */
2335
2336 bfd_boolean
2337 NAME (aout, squirt_out_relocs) (bfd *abfd, asection *section)
2338 {
2339   arelent **generic;
2340   unsigned char *native, *natptr;
2341   size_t each_size;
2342
2343   unsigned int count = section->reloc_count;
2344   bfd_size_type natsize;
2345
2346   if (count == 0 || section->orelocation == NULL)
2347     return TRUE;
2348
2349   each_size = obj_reloc_entry_size (abfd);
2350   natsize = (bfd_size_type) each_size * count;
2351   native = bfd_zalloc (abfd, natsize);
2352   if (!native)
2353     return FALSE;
2354
2355   generic = section->orelocation;
2356
2357   if (each_size == RELOC_EXT_SIZE)
2358     {
2359       for (natptr = native;
2360            count != 0;
2361            --count, natptr += each_size, ++generic)
2362         MY_swap_ext_reloc_out (abfd, *generic,
2363                                (struct reloc_ext_external *) natptr);
2364     }
2365   else
2366     {
2367       for (natptr = native;
2368            count != 0;
2369            --count, natptr += each_size, ++generic)
2370         MY_swap_std_reloc_out (abfd, *generic,
2371                                (struct reloc_std_external *) natptr);
2372     }
2373
2374   if (bfd_bwrite ((void *) native, natsize, abfd) != natsize)
2375     {
2376       bfd_release (abfd, native);
2377       return FALSE;
2378     }
2379   bfd_release (abfd, native);
2380
2381   return TRUE;
2382 }
2383
2384 /* This is stupid.  This function should be a boolean predicate.  */
2385
2386 long
2387 NAME (aout, canonicalize_reloc) (bfd *abfd,
2388                                  sec_ptr section,
2389                                  arelent **relptr,
2390                                  asymbol **symbols)
2391 {
2392   arelent *tblptr = section->relocation;
2393   unsigned int count;
2394
2395   if (section == obj_bsssec (abfd))
2396     {
2397       *relptr = NULL;
2398       return 0;
2399     }
2400
2401   if (!(tblptr || NAME (aout, slurp_reloc_table) (abfd, section, symbols)))
2402     return -1;
2403
2404   if (section->flags & SEC_CONSTRUCTOR)
2405     {
2406       arelent_chain *chain = section->constructor_chain;
2407       for (count = 0; count < section->reloc_count; count ++)
2408         {
2409           *relptr ++ = &chain->relent;
2410           chain = chain->next;
2411         }
2412     }
2413   else
2414     {
2415       tblptr = section->relocation;
2416
2417       for (count = 0; count++ < section->reloc_count; )
2418         {
2419           *relptr++ = tblptr++;
2420         }
2421     }
2422   *relptr = 0;
2423
2424   return section->reloc_count;
2425 }
2426
2427 long
2428 NAME (aout, get_reloc_upper_bound) (bfd *abfd, sec_ptr asect)
2429 {
2430   if (bfd_get_format (abfd) != bfd_object)
2431     {
2432       bfd_set_error (bfd_error_invalid_operation);
2433       return -1;
2434     }
2435
2436   if (asect->flags & SEC_CONSTRUCTOR)
2437     return sizeof (arelent *) * (asect->reloc_count + 1);
2438
2439   if (asect == obj_datasec (abfd))
2440     return sizeof (arelent *)
2441       * ((exec_hdr (abfd)->a_drsize / obj_reloc_entry_size (abfd))
2442          + 1);
2443
2444   if (asect == obj_textsec (abfd))
2445     return sizeof (arelent *)
2446       * ((exec_hdr (abfd)->a_trsize / obj_reloc_entry_size (abfd))
2447          + 1);
2448
2449   if (asect == obj_bsssec (abfd))
2450     return sizeof (arelent *);
2451
2452   if (asect == obj_bsssec (abfd))
2453     return 0;
2454
2455   bfd_set_error (bfd_error_invalid_operation);
2456   return -1;
2457 }
2458 \f
2459 long
2460 NAME (aout, get_symtab_upper_bound) (bfd *abfd)
2461 {
2462   if (!NAME (aout, slurp_symbol_table) (abfd))
2463     return -1;
2464
2465   return (bfd_get_symcount (abfd)+1) * (sizeof (aout_symbol_type *));
2466 }
2467
2468 alent *
2469 NAME (aout, get_lineno) (bfd *ignore_abfd ATTRIBUTE_UNUSED,
2470                          asymbol *ignore_symbol ATTRIBUTE_UNUSED)
2471 {
2472   return NULL;
2473 }
2474
2475 void
2476 NAME (aout, get_symbol_info) (bfd *ignore_abfd ATTRIBUTE_UNUSED,
2477                               asymbol *symbol,
2478                               symbol_info *ret)
2479 {
2480   bfd_symbol_info (symbol, ret);
2481
2482   if (ret->type == '?')
2483     {
2484       int type_code = aout_symbol (symbol)->type & 0xff;
2485       const char *stab_name = bfd_get_stab_name (type_code);
2486       static char buf[10];
2487
2488       if (stab_name == NULL)
2489         {
2490           sprintf (buf, "(%d)", type_code);
2491           stab_name = buf;
2492         }
2493       ret->type = '-';
2494       ret->stab_type = type_code;
2495       ret->stab_other = (unsigned) (aout_symbol (symbol)->other & 0xff);
2496       ret->stab_desc = (unsigned) (aout_symbol (symbol)->desc & 0xffff);
2497       ret->stab_name = stab_name;
2498     }
2499 }
2500
2501 void
2502 NAME (aout, print_symbol) (bfd *abfd,
2503                            void * afile,
2504                            asymbol *symbol,
2505                            bfd_print_symbol_type how)
2506 {
2507   FILE *file = (FILE *)afile;
2508
2509   switch (how)
2510     {
2511     case bfd_print_symbol_name:
2512       if (symbol->name)
2513         fprintf (file,"%s", symbol->name);
2514       break;
2515     case bfd_print_symbol_more:
2516       fprintf (file,"%4x %2x %2x",
2517                (unsigned) (aout_symbol (symbol)->desc & 0xffff),
2518                (unsigned) (aout_symbol (symbol)->other & 0xff),
2519                (unsigned) (aout_symbol (symbol)->type));
2520       break;
2521     case bfd_print_symbol_all:
2522       {
2523         const char *section_name = symbol->section->name;
2524
2525         bfd_print_symbol_vandf (abfd, (void *)file, symbol);
2526
2527         fprintf (file," %-5s %04x %02x %02x",
2528                  section_name,
2529                  (unsigned) (aout_symbol (symbol)->desc & 0xffff),
2530                  (unsigned) (aout_symbol (symbol)->other & 0xff),
2531                  (unsigned) (aout_symbol (symbol)->type & 0xff));
2532         if (symbol->name)
2533           fprintf (file," %s", symbol->name);
2534       }
2535       break;
2536     }
2537 }
2538
2539 /* If we don't have to allocate more than 1MB to hold the generic
2540    symbols, we use the generic minisymbol methord: it's faster, since
2541    it only translates the symbols once, not multiple times.  */
2542 #define MINISYM_THRESHOLD (1000000 / sizeof (asymbol))
2543
2544 /* Read minisymbols.  For minisymbols, we use the unmodified a.out
2545    symbols.  The minisymbol_to_symbol function translates these into
2546    BFD asymbol structures.  */
2547
2548 long
2549 NAME (aout, read_minisymbols) (bfd *abfd,
2550                                bfd_boolean dynamic,
2551                                void * *minisymsp,
2552                                unsigned int *sizep)
2553 {
2554   if (dynamic)
2555     /* We could handle the dynamic symbols here as well, but it's
2556        easier to hand them off.  */
2557     return _bfd_generic_read_minisymbols (abfd, dynamic, minisymsp, sizep);
2558
2559   if (! aout_get_external_symbols (abfd))
2560     return -1;
2561
2562   if (obj_aout_external_sym_count (abfd) < MINISYM_THRESHOLD)
2563     return _bfd_generic_read_minisymbols (abfd, dynamic, minisymsp, sizep);
2564
2565   *minisymsp = (void *) obj_aout_external_syms (abfd);
2566
2567   /* By passing the external symbols back from this routine, we are
2568      giving up control over the memory block.  Clear
2569      obj_aout_external_syms, so that we do not try to free it
2570      ourselves.  */
2571   obj_aout_external_syms (abfd) = NULL;
2572
2573   *sizep = EXTERNAL_NLIST_SIZE;
2574   return obj_aout_external_sym_count (abfd);
2575 }
2576
2577 /* Convert a minisymbol to a BFD asymbol.  A minisymbol is just an
2578    unmodified a.out symbol.  The SYM argument is a structure returned
2579    by bfd_make_empty_symbol, which we fill in here.  */
2580
2581 asymbol *
2582 NAME (aout, minisymbol_to_symbol) (bfd *abfd,
2583                                    bfd_boolean dynamic,
2584                                    const void * minisym,
2585                                    asymbol *sym)
2586 {
2587   if (dynamic
2588       || obj_aout_external_sym_count (abfd) < MINISYM_THRESHOLD)
2589     return _bfd_generic_minisymbol_to_symbol (abfd, dynamic, minisym, sym);
2590
2591   memset (sym, 0, sizeof (aout_symbol_type));
2592
2593   /* We call translate_symbol_table to translate a single symbol.  */
2594   if (! (NAME (aout, translate_symbol_table)
2595          (abfd,
2596           (aout_symbol_type *) sym,
2597           (struct external_nlist *) minisym,
2598           (bfd_size_type) 1,
2599           obj_aout_external_strings (abfd),
2600           obj_aout_external_string_size (abfd),
2601           FALSE)))
2602     return NULL;
2603
2604   return sym;
2605 }
2606
2607 /* Provided a BFD, a section and an offset into the section, calculate
2608    and return the name of the source file and the line nearest to the
2609    wanted location.  */
2610
2611 bfd_boolean
2612 NAME (aout, find_nearest_line) (bfd *abfd,
2613                                 asection *section,
2614                                 asymbol **symbols,
2615                                 bfd_vma offset,
2616                                 const char **filename_ptr,
2617                                 const char **functionname_ptr,
2618                                 unsigned int *line_ptr)
2619 {
2620   /* Run down the file looking for the filename, function and linenumber.  */
2621   asymbol **p;
2622   const char *directory_name = NULL;
2623   const char *main_file_name = NULL;
2624   const char *current_file_name = NULL;
2625   const char *line_file_name = NULL;      /* Value of current_file_name at line number.  */
2626   const char *line_directory_name = NULL; /* Value of directory_name at line number.  */
2627   bfd_vma low_line_vma = 0;
2628   bfd_vma low_func_vma = 0;
2629   asymbol *func = 0;
2630   bfd_size_type filelen, funclen;
2631   char *buf;
2632
2633   *filename_ptr = abfd->filename;
2634   *functionname_ptr = 0;
2635   *line_ptr = 0;
2636
2637   if (symbols != NULL)
2638     {
2639       for (p = symbols; *p; p++)
2640         {
2641           aout_symbol_type  *q = (aout_symbol_type *) (*p);
2642         next:
2643           switch (q->type)
2644             {
2645             case N_TEXT:
2646               /* If this looks like a file name symbol, and it comes after
2647                  the line number we have found so far, but before the
2648                  offset, then we have probably not found the right line
2649                  number.  */
2650               if (q->symbol.value <= offset
2651                   && ((q->symbol.value > low_line_vma
2652                        && (line_file_name != NULL
2653                            || *line_ptr != 0))
2654                       || (q->symbol.value > low_func_vma
2655                           && func != NULL)))
2656                 {
2657                   const char *symname;
2658
2659                   symname = q->symbol.name;
2660                   if (strcmp (symname + strlen (symname) - 2, ".o") == 0)
2661                     {
2662                       if (q->symbol.value > low_line_vma)
2663                         {
2664                           *line_ptr = 0;
2665                           line_file_name = NULL;
2666                         }
2667                       if (q->symbol.value > low_func_vma)
2668                         func = NULL;
2669                     }
2670                 }
2671               break;
2672
2673             case N_SO:
2674               /* If this symbol is less than the offset, but greater than
2675                  the line number we have found so far, then we have not
2676                  found the right line number.  */
2677               if (q->symbol.value <= offset)
2678                 {
2679                   if (q->symbol.value > low_line_vma)
2680                     {
2681                       *line_ptr = 0;
2682                       line_file_name = NULL;
2683                     }
2684                   if (q->symbol.value > low_func_vma)
2685                     func = NULL;
2686                 }
2687
2688               main_file_name = current_file_name = q->symbol.name;
2689               /* Look ahead to next symbol to check if that too is an N_SO.  */
2690               p++;
2691               if (*p == NULL)
2692                 goto done;
2693               q = (aout_symbol_type *) (*p);
2694               if (q->type != (int)N_SO)
2695                 goto next;
2696
2697               /* Found a second N_SO  First is directory; second is filename.  */
2698               directory_name = current_file_name;
2699               main_file_name = current_file_name = q->symbol.name;
2700               if (obj_textsec (abfd) != section)
2701                 goto done;
2702               break;
2703             case N_SOL:
2704               current_file_name = q->symbol.name;
2705               break;
2706
2707             case N_SLINE:
2708
2709             case N_DSLINE:
2710             case N_BSLINE:
2711               /* We'll keep this if it resolves nearer than the one we have
2712                  already.  */
2713               if (q->symbol.value >= low_line_vma
2714                   && q->symbol.value <= offset)
2715                 {
2716                   *line_ptr = q->desc;
2717                   low_line_vma = q->symbol.value;
2718                   line_file_name = current_file_name;
2719                   line_directory_name = directory_name;
2720                 }
2721               break;
2722             case N_FUN:
2723               {
2724                 /* We'll keep this if it is nearer than the one we have already.  */
2725                 if (q->symbol.value >= low_func_vma &&
2726                     q->symbol.value <= offset)
2727                   {
2728                     low_func_vma = q->symbol.value;
2729                     func = (asymbol *)q;
2730                   }
2731                 else if (q->symbol.value > offset)
2732                   goto done;
2733               }
2734               break;
2735             }
2736         }
2737     }
2738
2739  done:
2740   if (*line_ptr != 0)
2741     {
2742       main_file_name = line_file_name;
2743       directory_name = line_directory_name;
2744     }
2745
2746   if (main_file_name == NULL
2747       || IS_ABSOLUTE_PATH (main_file_name)
2748       || directory_name == NULL)
2749     filelen = 0;
2750   else
2751     filelen = strlen (directory_name) + strlen (main_file_name);
2752
2753   if (func == NULL)
2754     funclen = 0;
2755   else
2756     funclen = strlen (bfd_asymbol_name (func));
2757
2758   if (adata (abfd).line_buf != NULL)
2759     free (adata (abfd).line_buf);
2760
2761   if (filelen + funclen == 0)
2762     adata (abfd).line_buf = buf = NULL;
2763   else
2764     {
2765       buf = bfd_malloc (filelen + funclen + 3);
2766       adata (abfd).line_buf = buf;
2767       if (buf == NULL)
2768         return FALSE;
2769     }
2770
2771   if (main_file_name != NULL)
2772     {
2773       if (IS_ABSOLUTE_PATH (main_file_name) || directory_name == NULL)
2774         *filename_ptr = main_file_name;
2775       else
2776         {
2777           sprintf (buf, "%s%s", directory_name, main_file_name);
2778           *filename_ptr = buf;
2779           buf += filelen + 1;
2780         }
2781     }
2782
2783   if (func)
2784     {
2785       const char *function = func->name;
2786       char *colon;
2787
2788       /* The caller expects a symbol name.  We actually have a
2789          function name, without the leading underscore.  Put the
2790          underscore back in, so that the caller gets a symbol name.  */
2791       if (bfd_get_symbol_leading_char (abfd) == '\0')
2792         strcpy (buf, function);
2793       else
2794         {
2795           buf[0] = bfd_get_symbol_leading_char (abfd);
2796           strcpy (buf + 1, function);
2797         }
2798       /* Have to remove : stuff.  */
2799       colon = strchr (buf, ':');
2800       if (colon != NULL)
2801         *colon = '\0';
2802       *functionname_ptr = buf;
2803     }
2804
2805   return TRUE;
2806 }
2807
2808 int
2809 NAME (aout, sizeof_headers) (bfd *abfd,
2810                              struct bfd_link_info *info ATTRIBUTE_UNUSED)
2811 {
2812   return adata (abfd).exec_bytes_size;
2813 }
2814
2815 /* Free all information we have cached for this BFD.  We can always
2816    read it again later if we need it.  */
2817
2818 bfd_boolean
2819 NAME (aout, bfd_free_cached_info) (bfd *abfd)
2820 {
2821   asection *o;
2822
2823   if (bfd_get_format (abfd) != bfd_object
2824       || abfd->tdata.aout_data == NULL)
2825     return TRUE;
2826
2827 #define BFCI_FREE(x) if (x != NULL) { free (x); x = NULL; }
2828   BFCI_FREE (obj_aout_symbols (abfd));
2829 #ifdef USE_MMAP
2830   obj_aout_external_syms (abfd) = 0;
2831   bfd_free_window (&obj_aout_sym_window (abfd));
2832   bfd_free_window (&obj_aout_string_window (abfd));
2833   obj_aout_external_strings (abfd) = 0;
2834 #else
2835   BFCI_FREE (obj_aout_external_syms (abfd));
2836   BFCI_FREE (obj_aout_external_strings (abfd));
2837 #endif
2838   for (o = abfd->sections; o != NULL; o = o->next)
2839     BFCI_FREE (o->relocation);
2840 #undef BFCI_FREE
2841
2842   return TRUE;
2843 }
2844 \f
2845 /* a.out link code.  */
2846
2847 /* Routine to create an entry in an a.out link hash table.  */
2848
2849 struct bfd_hash_entry *
2850 NAME (aout, link_hash_newfunc) (struct bfd_hash_entry *entry,
2851                                 struct bfd_hash_table *table,
2852                                 const char *string)
2853 {
2854   struct aout_link_hash_entry *ret = (struct aout_link_hash_entry *) entry;
2855
2856   /* Allocate the structure if it has not already been allocated by a
2857      subclass.  */
2858   if (ret == NULL)
2859     ret = bfd_hash_allocate (table, sizeof (* ret));
2860   if (ret == NULL)
2861     return NULL;
2862
2863   /* Call the allocation method of the superclass.  */
2864   ret = ((struct aout_link_hash_entry *)
2865          _bfd_link_hash_newfunc ((struct bfd_hash_entry *) ret,
2866                                  table, string));
2867   if (ret)
2868     {
2869       /* Set local fields.  */
2870       ret->written = FALSE;
2871       ret->indx = -1;
2872     }
2873
2874   return (struct bfd_hash_entry *) ret;
2875 }
2876
2877 /* Initialize an a.out link hash table.  */
2878
2879 bfd_boolean
2880 NAME (aout, link_hash_table_init) (struct aout_link_hash_table *table,
2881                                    bfd *abfd,
2882                                    struct bfd_hash_entry *(*newfunc)
2883                                    (struct bfd_hash_entry *, struct bfd_hash_table *,
2884                                     const char *),
2885                                    unsigned int entsize)
2886 {
2887   return _bfd_link_hash_table_init (&table->root, abfd, newfunc, entsize);
2888 }
2889
2890 /* Create an a.out link hash table.  */
2891
2892 struct bfd_link_hash_table *
2893 NAME (aout, link_hash_table_create) (bfd *abfd)
2894 {
2895   struct aout_link_hash_table *ret;
2896   bfd_size_type amt = sizeof (* ret);
2897
2898   ret = bfd_malloc (amt);
2899   if (ret == NULL)
2900     return NULL;
2901
2902   if (!NAME (aout, link_hash_table_init) (ret, abfd,
2903                                           NAME (aout, link_hash_newfunc),
2904                                           sizeof (struct aout_link_hash_entry)))
2905     {
2906       free (ret);
2907       return NULL;
2908     }
2909   return &ret->root;
2910 }
2911
2912 /* Add all symbols from an object file to the hash table.  */
2913
2914 static bfd_boolean
2915 aout_link_add_symbols (bfd *abfd, struct bfd_link_info *info)
2916 {
2917   bfd_boolean (*add_one_symbol)
2918     (struct bfd_link_info *, bfd *, const char *, flagword, asection *,
2919              bfd_vma, const char *, bfd_boolean, bfd_boolean,
2920              struct bfd_link_hash_entry **);
2921   struct external_nlist *syms;
2922   bfd_size_type sym_count;
2923   char *strings;
2924   bfd_boolean copy;
2925   struct aout_link_hash_entry **sym_hash;
2926   struct external_nlist *p;
2927   struct external_nlist *pend;
2928   bfd_size_type amt;
2929
2930   syms = obj_aout_external_syms (abfd);
2931   sym_count = obj_aout_external_sym_count (abfd);
2932   strings = obj_aout_external_strings (abfd);
2933   if (info->keep_memory)
2934     copy = FALSE;
2935   else
2936     copy = TRUE;
2937
2938   if (aout_backend_info (abfd)->add_dynamic_symbols != NULL)
2939     {
2940       if (! ((*aout_backend_info (abfd)->add_dynamic_symbols)
2941              (abfd, info, &syms, &sym_count, &strings)))
2942         return FALSE;
2943     }
2944
2945   /* We keep a list of the linker hash table entries that correspond
2946      to particular symbols.  We could just look them up in the hash
2947      table, but keeping the list is more efficient.  Perhaps this
2948      should be conditional on info->keep_memory.  */
2949   amt = sym_count * sizeof (struct aout_link_hash_entry *);
2950   sym_hash = bfd_alloc (abfd, amt);
2951   if (sym_hash == NULL && sym_count != 0)
2952     return FALSE;
2953   obj_aout_sym_hashes (abfd) = sym_hash;
2954
2955   add_one_symbol = aout_backend_info (abfd)->add_one_symbol;
2956   if (add_one_symbol == NULL)
2957     add_one_symbol = _bfd_generic_link_add_one_symbol;
2958
2959   p = syms;
2960   pend = p + sym_count;
2961   for (; p < pend; p++, sym_hash++)
2962     {
2963       int type;
2964       const char *name;
2965       bfd_vma value;
2966       asection *section;
2967       flagword flags;
2968       const char *string;
2969
2970       *sym_hash = NULL;
2971
2972       type = H_GET_8 (abfd, p->e_type);
2973
2974       /* Ignore debugging symbols.  */
2975       if ((type & N_STAB) != 0)
2976         continue;
2977
2978       name = strings + GET_WORD (abfd, p->e_strx);
2979       value = GET_WORD (abfd, p->e_value);
2980       flags = BSF_GLOBAL;
2981       string = NULL;
2982       switch (type)
2983         {
2984         default:
2985           abort ();
2986
2987         case N_UNDF:
2988         case N_ABS:
2989         case N_TEXT:
2990         case N_DATA:
2991         case N_BSS:
2992         case N_FN_SEQ:
2993         case N_COMM:
2994         case N_SETV:
2995         case N_FN:
2996           /* Ignore symbols that are not externally visible.  */
2997           continue;
2998         case N_INDR:
2999           /* Ignore local indirect symbol.  */
3000           ++p;
3001           ++sym_hash;
3002           continue;
3003
3004         case N_UNDF | N_EXT:
3005           if (value == 0)
3006             {
3007               section = bfd_und_section_ptr;
3008               flags = 0;
3009             }
3010           else
3011             section = bfd_com_section_ptr;
3012           break;
3013         case N_ABS | N_EXT:
3014           section = bfd_abs_section_ptr;
3015           break;
3016         case N_TEXT | N_EXT:
3017           section = obj_textsec (abfd);
3018           value -= bfd_get_section_vma (abfd, section);
3019           break;
3020         case N_DATA | N_EXT:
3021         case N_SETV | N_EXT:
3022           /* Treat N_SETV symbols as N_DATA symbol; see comment in
3023              translate_from_native_sym_flags.  */
3024           section = obj_datasec (abfd);
3025           value -= bfd_get_section_vma (abfd, section);
3026           break;
3027         case N_BSS | N_EXT:
3028           section = obj_bsssec (abfd);
3029           value -= bfd_get_section_vma (abfd, section);
3030           break;
3031         case N_INDR | N_EXT:
3032           /* An indirect symbol.  The next symbol is the symbol
3033              which this one really is.  */
3034           BFD_ASSERT (p + 1 < pend);
3035           ++p;
3036           string = strings + GET_WORD (abfd, p->e_strx);
3037           section = bfd_ind_section_ptr;
3038           flags |= BSF_INDIRECT;
3039           break;
3040         case N_COMM | N_EXT:
3041           section = bfd_com_section_ptr;
3042           break;
3043         case N_SETA: case N_SETA | N_EXT:
3044           section = bfd_abs_section_ptr;
3045           flags |= BSF_CONSTRUCTOR;
3046           break;
3047         case N_SETT: case N_SETT | N_EXT:
3048           section = obj_textsec (abfd);
3049           flags |= BSF_CONSTRUCTOR;
3050           value -= bfd_get_section_vma (abfd, section);
3051           break;
3052         case N_SETD: case N_SETD | N_EXT:
3053           section = obj_datasec (abfd);
3054           flags |= BSF_CONSTRUCTOR;
3055           value -= bfd_get_section_vma (abfd, section);
3056           break;
3057         case N_SETB: case N_SETB | N_EXT:
3058           section = obj_bsssec (abfd);
3059           flags |= BSF_CONSTRUCTOR;
3060           value -= bfd_get_section_vma (abfd, section);
3061           break;
3062         case N_WARNING:
3063           /* A warning symbol.  The next symbol is the one to warn
3064              about.  If there is no next symbol, just look away.  */
3065           if (p + 1 >= pend)
3066             return TRUE;
3067           ++p;
3068           string = name;
3069           name = strings + GET_WORD (abfd, p->e_strx);
3070           section = bfd_und_section_ptr;
3071           flags |= BSF_WARNING;
3072           break;
3073         case N_WEAKU:
3074           section = bfd_und_section_ptr;
3075           flags = BSF_WEAK;
3076           break;
3077         case N_WEAKA:
3078           section = bfd_abs_section_ptr;
3079           flags = BSF_WEAK;
3080           break;
3081         case N_WEAKT:
3082           section = obj_textsec (abfd);
3083           value -= bfd_get_section_vma (abfd, section);
3084           flags = BSF_WEAK;
3085           break;
3086         case N_WEAKD:
3087           section = obj_datasec (abfd);
3088           value -= bfd_get_section_vma (abfd, section);
3089           flags = BSF_WEAK;
3090           break;
3091         case N_WEAKB:
3092           section = obj_bsssec (abfd);
3093           value -= bfd_get_section_vma (abfd, section);
3094           flags = BSF_WEAK;
3095           break;
3096         }
3097
3098       if (! ((*add_one_symbol)
3099              (info, abfd, name, flags, section, value, string, copy, FALSE,
3100               (struct bfd_link_hash_entry **) sym_hash)))
3101         return FALSE;
3102
3103       /* Restrict the maximum alignment of a common symbol based on
3104          the architecture, since a.out has no way to represent
3105          alignment requirements of a section in a .o file.  FIXME:
3106          This isn't quite right: it should use the architecture of the
3107          output file, not the input files.  */
3108       if ((*sym_hash)->root.type == bfd_link_hash_common
3109           && ((*sym_hash)->root.u.c.p->alignment_power >
3110               bfd_get_arch_info (abfd)->section_align_power))
3111         (*sym_hash)->root.u.c.p->alignment_power =
3112           bfd_get_arch_info (abfd)->section_align_power;
3113
3114       /* If this is a set symbol, and we are not building sets, then
3115          it is possible for the hash entry to not have been set.  In
3116          such a case, treat the symbol as not globally defined.  */
3117       if ((*sym_hash)->root.type == bfd_link_hash_new)
3118         {
3119           BFD_ASSERT ((flags & BSF_CONSTRUCTOR) != 0);
3120           *sym_hash = NULL;
3121         }
3122
3123       if (type == (N_INDR | N_EXT) || type == N_WARNING)
3124         ++sym_hash;
3125     }
3126
3127   return TRUE;
3128 }
3129
3130 /* Free up the internal symbols read from an a.out file.  */
3131
3132 static bfd_boolean
3133 aout_link_free_symbols (bfd *abfd)
3134 {
3135   if (obj_aout_external_syms (abfd) != NULL)
3136     {
3137 #ifdef USE_MMAP
3138       bfd_free_window (&obj_aout_sym_window (abfd));
3139 #else
3140       free ((void *) obj_aout_external_syms (abfd));
3141 #endif
3142       obj_aout_external_syms (abfd) = NULL;
3143     }
3144   if (obj_aout_external_strings (abfd) != NULL)
3145     {
3146 #ifdef USE_MMAP
3147       bfd_free_window (&obj_aout_string_window (abfd));
3148 #else
3149       free ((void *) obj_aout_external_strings (abfd));
3150 #endif
3151       obj_aout_external_strings (abfd) = NULL;
3152     }
3153   return TRUE;
3154 }
3155
3156 /* Add symbols from an a.out object file.  */
3157
3158 static bfd_boolean
3159 aout_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info)
3160 {
3161   if (! aout_get_external_symbols (abfd))
3162     return FALSE;
3163   if (! aout_link_add_symbols (abfd, info))
3164     return FALSE;
3165   if (! info->keep_memory)
3166     {
3167       if (! aout_link_free_symbols (abfd))
3168         return FALSE;
3169     }
3170   return TRUE;
3171 }
3172
3173 /* Look through the internal symbols to see if this object file should
3174    be included in the link.  We should include this object file if it
3175    defines any symbols which are currently undefined.  If this object
3176    file defines a common symbol, then we may adjust the size of the
3177    known symbol but we do not include the object file in the link
3178    (unless there is some other reason to include it).  */
3179
3180 static bfd_boolean
3181 aout_link_check_ar_symbols (bfd *abfd,
3182                             struct bfd_link_info *info,
3183                             bfd_boolean *pneeded)
3184 {
3185   struct external_nlist *p;
3186   struct external_nlist *pend;
3187   char *strings;
3188
3189   *pneeded = FALSE;
3190
3191   /* Look through all the symbols.  */
3192   p = obj_aout_external_syms (abfd);
3193   pend = p + obj_aout_external_sym_count (abfd);
3194   strings = obj_aout_external_strings (abfd);
3195   for (; p < pend; p++)
3196     {
3197       int type = H_GET_8 (abfd, p->e_type);
3198       const char *name;
3199       struct bfd_link_hash_entry *h;
3200
3201       /* Ignore symbols that are not externally visible.  This is an
3202          optimization only, as we check the type more thoroughly
3203          below.  */
3204       if (((type & N_EXT) == 0
3205            || (type & N_STAB) != 0
3206            || type == N_FN)
3207           && type != N_WEAKA
3208           && type != N_WEAKT
3209           && type != N_WEAKD
3210           && type != N_WEAKB)
3211         {
3212           if (type == N_WARNING
3213               || type == N_INDR)
3214             ++p;
3215           continue;
3216         }
3217
3218       name = strings + GET_WORD (abfd, p->e_strx);
3219       h = bfd_link_hash_lookup (info->hash, name, FALSE, FALSE, TRUE);
3220
3221       /* We are only interested in symbols that are currently
3222          undefined or common.  */
3223       if (h == NULL
3224           || (h->type != bfd_link_hash_undefined
3225               && h->type != bfd_link_hash_common))
3226         {
3227           if (type == (N_INDR | N_EXT))
3228             ++p;
3229           continue;
3230         }
3231
3232       if (type == (N_TEXT | N_EXT)
3233           || type == (N_DATA | N_EXT)
3234           || type == (N_BSS | N_EXT)
3235           || type == (N_ABS | N_EXT)
3236           || type == (N_INDR | N_EXT))
3237         {
3238           /* This object file defines this symbol.  We must link it
3239              in.  This is true regardless of whether the current
3240              definition of the symbol is undefined or common.
3241
3242              If the current definition is common, we have a case in
3243              which we have already seen an object file including:
3244                  int a;
3245              and this object file from the archive includes:
3246                  int a = 5;
3247              In such a case, whether to include this object is target
3248              dependant for backward compatibility.
3249
3250              FIXME: The SunOS 4.1.3 linker will pull in the archive
3251              element if the symbol is defined in the .data section,
3252              but not if it is defined in the .text section.  That
3253              seems a bit crazy to me, and it has not been implemented
3254              yet.  However, it might be correct.  */
3255           if (h->type == bfd_link_hash_common)
3256             {
3257               int skip = 0;
3258
3259               switch (info->common_skip_ar_aymbols)
3260                 {
3261                 case bfd_link_common_skip_text:
3262                   skip = (type == (N_TEXT | N_EXT));
3263                   break;
3264                 case bfd_link_common_skip_data:
3265                   skip = (type == (N_DATA | N_EXT));
3266                   break;
3267                 default:
3268                 case bfd_link_common_skip_all:
3269                   skip = 1;
3270                   break;
3271                 }
3272
3273               if (skip)
3274                 continue;
3275             }
3276
3277           if (! (*info->callbacks->add_archive_element) (info, abfd, name))
3278             return FALSE;
3279           *pneeded = TRUE;
3280           return TRUE;
3281         }
3282
3283       if (type == (N_UNDF | N_EXT))
3284         {
3285           bfd_vma value;
3286
3287           value = GET_WORD (abfd, p->e_value);
3288           if (value != 0)
3289             {
3290               /* This symbol is common in the object from the archive
3291                  file.  */
3292               if (h->type == bfd_link_hash_undefined)
3293                 {
3294                   bfd *symbfd;
3295                   unsigned int power;
3296
3297                   symbfd = h->u.undef.abfd;
3298                   if (symbfd == NULL)
3299                     {
3300                       /* This symbol was created as undefined from
3301                          outside BFD.  We assume that we should link
3302                          in the object file.  This is done for the -u
3303                          option in the linker.  */
3304                       if (! (*info->callbacks->add_archive_element) (info,
3305                                                                      abfd,
3306                                                                      name))
3307                         return FALSE;
3308                       *pneeded = TRUE;
3309                       return TRUE;
3310                     }
3311                   /* Turn the current link symbol into a common
3312                      symbol.  It is already on the undefs list.  */
3313                   h->type = bfd_link_hash_common;
3314                   h->u.c.p = bfd_hash_allocate (&info->hash->table,
3315                                                 sizeof (struct bfd_link_hash_common_entry));
3316                   if (h->u.c.p == NULL)
3317                     return FALSE;
3318
3319                   h->u.c.size = value;
3320
3321                   /* FIXME: This isn't quite right.  The maximum
3322                      alignment of a common symbol should be set by the
3323                      architecture of the output file, not of the input
3324                      file.  */
3325                   power = bfd_log2 (value);
3326                   if (power > bfd_get_arch_info (abfd)->section_align_power)
3327                     power = bfd_get_arch_info (abfd)->section_align_power;
3328                   h->u.c.p->alignment_power = power;
3329
3330                   h->u.c.p->section = bfd_make_section_old_way (symbfd,
3331                                                                 "COMMON");
3332                 }
3333               else
3334                 {
3335                   /* Adjust the size of the common symbol if
3336                      necessary.  */
3337                   if (value > h->u.c.size)
3338                     h->u.c.size = value;
3339                 }
3340             }
3341         }
3342
3343       if (type == N_WEAKA
3344           || type == N_WEAKT
3345           || type == N_WEAKD
3346           || type == N_WEAKB)
3347         {
3348           /* This symbol is weak but defined.  We must pull it in if
3349              the current link symbol is undefined, but we don't want
3350              it if the current link symbol is common.  */
3351           if (h->type == bfd_link_hash_undefined)
3352             {
3353               if (! (*info->callbacks->add_archive_element) (info, abfd, name))
3354                 return FALSE;
3355               *pneeded = TRUE;
3356               return TRUE;
3357             }
3358         }
3359     }
3360
3361   /* We do not need this object file.  */
3362   return TRUE;
3363 }
3364 /* Check a single archive element to see if we need to include it in
3365    the link.  *PNEEDED is set according to whether this element is
3366    needed in the link or not.  This is called from
3367    _bfd_generic_link_add_archive_symbols.  */
3368
3369 static bfd_boolean
3370 aout_link_check_archive_element (bfd *abfd,
3371                                  struct bfd_link_info *info,
3372                                  bfd_boolean *pneeded)
3373 {
3374   if (! aout_get_external_symbols (abfd))
3375     return FALSE;
3376
3377   if (! aout_link_check_ar_symbols (abfd, info, pneeded))
3378     return FALSE;
3379
3380   if (*pneeded)
3381     {
3382       if (! aout_link_add_symbols (abfd, info))
3383         return FALSE;
3384     }
3385
3386   if (! info->keep_memory || ! *pneeded)
3387     {
3388       if (! aout_link_free_symbols (abfd))
3389         return FALSE;
3390     }
3391
3392   return TRUE;
3393 }
3394
3395 /* Given an a.out BFD, add symbols to the global hash table as
3396    appropriate.  */
3397
3398 bfd_boolean
3399 NAME (aout, link_add_symbols) (bfd *abfd, struct bfd_link_info *info)
3400 {
3401   switch (bfd_get_format (abfd))
3402     {
3403     case bfd_object:
3404       return aout_link_add_object_symbols (abfd, info);
3405     case bfd_archive:
3406       return _bfd_generic_link_add_archive_symbols
3407         (abfd, info, aout_link_check_archive_element);
3408     default:
3409       bfd_set_error (bfd_error_wrong_format);
3410       return FALSE;
3411     }
3412 }
3413 \f
3414 /* A hash table used for header files with N_BINCL entries.  */
3415
3416 struct aout_link_includes_table
3417 {
3418   struct bfd_hash_table root;
3419 };
3420
3421 /* A linked list of totals that we have found for a particular header
3422    file.  */
3423
3424 struct aout_link_includes_totals
3425 {
3426   struct aout_link_includes_totals *next;
3427   bfd_vma total;
3428 };
3429
3430 /* An entry in the header file hash table.  */
3431
3432 struct aout_link_includes_entry
3433 {
3434   struct bfd_hash_entry root;
3435   /* List of totals we have found for this file.  */
3436   struct aout_link_includes_totals *totals;
3437 };
3438
3439 /* Look up an entry in an the header file hash table.  */
3440
3441 #define aout_link_includes_lookup(table, string, create, copy)          \
3442   ((struct aout_link_includes_entry *)                                  \
3443    bfd_hash_lookup (&(table)->root, (string), (create), (copy)))
3444
3445 /* During the final link step we need to pass around a bunch of
3446    information, so we do it in an instance of this structure.  */
3447
3448 struct aout_final_link_info
3449 {
3450   /* General link information.  */
3451   struct bfd_link_info *info;
3452   /* Output bfd.  */
3453   bfd *output_bfd;
3454   /* Reloc file positions.  */
3455   file_ptr treloff, dreloff;
3456   /* File position of symbols.  */
3457   file_ptr symoff;
3458   /* String table.  */
3459   struct bfd_strtab_hash *strtab;
3460   /* Header file hash table.  */
3461   struct aout_link_includes_table includes;
3462   /* A buffer large enough to hold the contents of any section.  */
3463   bfd_byte *contents;
3464   /* A buffer large enough to hold the relocs of any section.  */
3465   void * relocs;
3466   /* A buffer large enough to hold the symbol map of any input BFD.  */
3467   int *symbol_map;
3468   /* A buffer large enough to hold output symbols of any input BFD.  */
3469   struct external_nlist *output_syms;
3470 };
3471
3472 /* The function to create a new entry in the header file hash table.  */
3473
3474 static struct bfd_hash_entry *
3475 aout_link_includes_newfunc (struct bfd_hash_entry *entry,
3476                             struct bfd_hash_table *table,
3477                             const char *string)
3478 {
3479   struct aout_link_includes_entry *ret =
3480     (struct aout_link_includes_entry *) entry;
3481
3482   /* Allocate the structure if it has not already been allocated by a
3483      subclass.  */
3484   if (ret == NULL)
3485     ret = bfd_hash_allocate (table, sizeof (* ret));
3486   if (ret == NULL)
3487     return NULL;
3488
3489   /* Call the allocation method of the superclass.  */
3490   ret = ((struct aout_link_includes_entry *)
3491          bfd_hash_newfunc ((struct bfd_hash_entry *) ret, table, string));
3492   if (ret)
3493     {
3494       /* Set local fields.  */
3495       ret->totals = NULL;
3496     }
3497
3498   return (struct bfd_hash_entry *) ret;
3499 }
3500
3501 /* Write out a symbol that was not associated with an a.out input
3502    object.  */
3503
3504 static bfd_boolean
3505 aout_link_write_other_symbol (struct aout_link_hash_entry *h, void * data)
3506 {
3507   struct aout_final_link_info *finfo = (struct aout_final_link_info *) data;
3508   bfd *output_bfd;
3509   int type;
3510   bfd_vma val;
3511   struct external_nlist outsym;
3512   bfd_size_type indx;
3513   bfd_size_type amt;
3514
3515   if (h->root.type == bfd_link_hash_warning)
3516     {
3517       h = (struct aout_link_hash_entry *) h->root.u.i.link;
3518       if (h->root.type == bfd_link_hash_new)
3519         return TRUE;
3520     }
3521
3522   output_bfd = finfo->output_bfd;
3523
3524   if (aout_backend_info (output_bfd)->write_dynamic_symbol != NULL)
3525     {
3526       if (! ((*aout_backend_info (output_bfd)->write_dynamic_symbol)
3527              (output_bfd, finfo->info, h)))
3528         {
3529           /* FIXME: No way to handle errors.  */
3530           abort ();
3531         }
3532     }
3533
3534   if (h->written)
3535     return TRUE;
3536
3537   h->written = TRUE;
3538
3539   /* An indx of -2 means the symbol must be written.  */
3540   if (h->indx != -2
3541       && (finfo->info->strip == strip_all
3542           || (finfo->info->strip == strip_some
3543               && bfd_hash_lookup (finfo->info->keep_hash, h->root.root.string,
3544                                   FALSE, FALSE) == NULL)))
3545     return TRUE;
3546
3547   switch (h->root.type)
3548     {
3549     default:
3550     case bfd_link_hash_warning:
3551       abort ();
3552       /* Avoid variable not initialized warnings.  */
3553       return TRUE;
3554     case bfd_link_hash_new:
3555       /* This can happen for set symbols when sets are not being
3556          built.  */
3557       return TRUE;
3558     case bfd_link_hash_undefined:
3559       type = N_UNDF | N_EXT;
3560       val = 0;
3561       break;
3562     case bfd_link_hash_defined:
3563     case bfd_link_hash_defweak:
3564       {
3565         asection *sec;
3566
3567         sec = h->root.u.def.section->output_section;
3568         BFD_ASSERT (bfd_is_abs_section (sec)
3569                     || sec->owner == output_bfd);
3570         if (sec == obj_textsec (output_bfd))
3571           type = h->root.type == bfd_link_hash_defined ? N_TEXT : N_WEAKT;
3572         else if (sec == obj_datasec (output_bfd))
3573           type = h->root.type == bfd_link_hash_defined ? N_DATA : N_WEAKD;
3574         else if (sec == obj_bsssec (output_bfd))
3575           type = h->root.type == bfd_link_hash_defined ? N_BSS : N_WEAKB;
3576         else
3577           type = h->root.type == bfd_link_hash_defined ? N_ABS : N_WEAKA;
3578         type |= N_EXT;
3579         val = (h->root.u.def.value
3580                + sec->vma
3581                + h->root.u.def.section->output_offset);
3582       }
3583       break;
3584     case bfd_link_hash_common:
3585       type = N_UNDF | N_EXT;
3586       val = h->root.u.c.size;
3587       break;
3588     case bfd_link_hash_undefweak:
3589       type = N_WEAKU;
3590       val = 0;
3591     case bfd_link_hash_indirect:
3592       /* We ignore these symbols, since the indirected symbol is
3593          already in the hash table.  */
3594       return TRUE;
3595     }
3596
3597   H_PUT_8 (output_bfd, type, outsym.e_type);
3598   H_PUT_8 (output_bfd, 0, outsym.e_other);
3599   H_PUT_16 (output_bfd, 0, outsym.e_desc);
3600   indx = add_to_stringtab (output_bfd, finfo->strtab, h->root.root.string,
3601                            FALSE);
3602   if (indx == - (bfd_size_type) 1)
3603     /* FIXME: No way to handle errors.  */
3604     abort ();
3605
3606   PUT_WORD (output_bfd, indx, outsym.e_strx);
3607   PUT_WORD (output_bfd, val, outsym.e_value);
3608
3609   amt = EXTERNAL_NLIST_SIZE;
3610   if (bfd_seek (output_bfd, finfo->symoff, SEEK_SET) != 0
3611       || bfd_bwrite ((void *) &outsym, amt, output_bfd) != amt)
3612     /* FIXME: No way to handle errors.  */
3613     abort ();
3614
3615   finfo->symoff += EXTERNAL_NLIST_SIZE;
3616   h->indx = obj_aout_external_sym_count (output_bfd);
3617   ++obj_aout_external_sym_count (output_bfd);
3618
3619   return TRUE;
3620 }
3621
3622 /* Handle a link order which is supposed to generate a reloc.  */
3623
3624 static bfd_boolean
3625 aout_link_reloc_link_order (struct aout_final_link_info *finfo,
3626                             asection *o,
3627                             struct bfd_link_order *p)
3628 {
3629   struct bfd_link_order_reloc *pr;
3630   int r_index;
3631   int r_extern;
3632   reloc_howto_type *howto;
3633   file_ptr *reloff_ptr = NULL;
3634   struct reloc_std_external srel;
3635   struct reloc_ext_external erel;
3636   void * rel_ptr;
3637   bfd_size_type amt;
3638
3639   pr = p->u.reloc.p;
3640
3641   if (p->type == bfd_section_reloc_link_order)
3642     {
3643       r_extern = 0;
3644       if (bfd_is_abs_section (pr->u.section))
3645         r_index = N_ABS | N_EXT;
3646       else
3647         {
3648           BFD_ASSERT (pr->u.section->owner == finfo->output_bfd);
3649           r_index = pr->u.section->target_index;
3650         }
3651     }
3652   else
3653     {
3654       struct aout_link_hash_entry *h;
3655
3656       BFD_ASSERT (p->type == bfd_symbol_reloc_link_order);
3657       r_extern = 1;
3658       h = ((struct aout_link_hash_entry *)
3659            bfd_wrapped_link_hash_lookup (finfo->output_bfd, finfo->info,
3660                                          pr->u.name, FALSE, FALSE, TRUE));
3661       if (h != NULL
3662           && h->indx >= 0)
3663         r_index = h->indx;
3664       else if (h != NULL)
3665         {
3666           /* We decided to strip this symbol, but it turns out that we
3667              can't.  Note that we lose the other and desc information
3668              here.  I don't think that will ever matter for a global
3669              symbol.  */
3670           h->indx = -2;
3671           h->written = FALSE;
3672           if (! aout_link_write_other_symbol (h, (void *) finfo))
3673             return FALSE;
3674           r_index = h->indx;
3675         }
3676       else
3677         {
3678           if (! ((*finfo->info->callbacks->unattached_reloc)
3679                  (finfo->info, pr->u.name, NULL, NULL, (bfd_vma) 0)))
3680             return FALSE;
3681           r_index = 0;
3682         }
3683     }
3684
3685   howto = bfd_reloc_type_lookup (finfo->output_bfd, pr->reloc);
3686   if (howto == 0)
3687     {
3688       bfd_set_error (bfd_error_bad_value);
3689       return FALSE;
3690     }
3691
3692   if (o == obj_textsec (finfo->output_bfd))
3693     reloff_ptr = &finfo->treloff;
3694   else if (o == obj_datasec (finfo->output_bfd))
3695     reloff_ptr = &finfo->dreloff;
3696   else
3697     abort ();
3698
3699   if (obj_reloc_entry_size (finfo->output_bfd) == RELOC_STD_SIZE)
3700     {
3701 #ifdef MY_put_reloc
3702       MY_put_reloc (finfo->output_bfd, r_extern, r_index, p->offset, howto,
3703                     &srel);
3704 #else
3705       {
3706         int r_pcrel;
3707         int r_baserel;
3708         int r_jmptable;
3709         int r_relative;
3710         int r_length;
3711
3712         r_pcrel = (int) howto->pc_relative;
3713         r_baserel = (howto->type & 8) != 0;
3714         r_jmptable = (howto->type & 16) != 0;
3715         r_relative = (howto->type & 32) != 0;
3716         r_length = howto->size;
3717
3718         PUT_WORD (finfo->output_bfd, p->offset, srel.r_address);
3719         if (bfd_header_big_endian (finfo->output_bfd))
3720           {
3721             srel.r_index[0] = r_index >> 16;
3722             srel.r_index[1] = r_index >> 8;
3723             srel.r_index[2] = r_index;
3724             srel.r_type[0] =
3725               ((r_extern ?     RELOC_STD_BITS_EXTERN_BIG : 0)
3726                | (r_pcrel ?    RELOC_STD_BITS_PCREL_BIG : 0)
3727                | (r_baserel ?  RELOC_STD_BITS_BASEREL_BIG : 0)
3728                | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_BIG : 0)
3729                | (r_relative ? RELOC_STD_BITS_RELATIVE_BIG : 0)
3730                | (r_length <<  RELOC_STD_BITS_LENGTH_SH_BIG));
3731           }
3732         else
3733           {
3734             srel.r_index[2] = r_index >> 16;
3735             srel.r_index[1] = r_index >> 8;
3736             srel.r_index[0] = r_index;
3737             srel.r_type[0] =
3738               ((r_extern ?     RELOC_STD_BITS_EXTERN_LITTLE : 0)
3739                | (r_pcrel ?    RELOC_STD_BITS_PCREL_LITTLE : 0)
3740                | (r_baserel ?  RELOC_STD_BITS_BASEREL_LITTLE : 0)
3741                | (r_jmptable ? RELOC_STD_BITS_JMPTABLE_LITTLE : 0)
3742                | (r_relative ? RELOC_STD_BITS_RELATIVE_LITTLE : 0)
3743                | (r_length <<  RELOC_STD_BITS_LENGTH_SH_LITTLE));
3744           }
3745       }
3746 #endif
3747       rel_ptr = (void *) &srel;
3748
3749       /* We have to write the addend into the object file, since
3750          standard a.out relocs are in place.  It would be more
3751          reliable if we had the current contents of the file here,
3752          rather than assuming zeroes, but we can't read the file since
3753          it was opened using bfd_openw.  */
3754       if (pr->addend != 0)
3755         {
3756           bfd_size_type size;
3757           bfd_reloc_status_type r;
3758           bfd_byte *buf;
3759           bfd_boolean ok;
3760
3761           size = bfd_get_reloc_size (howto);
3762           buf = bfd_zmalloc (size);
3763           if (buf == NULL)
3764             return FALSE;
3765           r = MY_relocate_contents (howto, finfo->output_bfd,
3766                                     (bfd_vma) pr->addend, buf);
3767           switch (r)
3768             {
3769             case bfd_reloc_ok:
3770               break;
3771             default:
3772             case bfd_reloc_outofrange:
3773               abort ();
3774             case bfd_reloc_overflow:
3775               if (! ((*finfo->info->callbacks->reloc_overflow)
3776                      (finfo->info, NULL,
3777                       (p->type == bfd_section_reloc_link_order
3778                        ? bfd_section_name (finfo->output_bfd,
3779                                            pr->u.section)
3780                        : pr->u.name),
3781                       howto->name, pr->addend, NULL, NULL, (bfd_vma) 0)))
3782                 {
3783                   free (buf);
3784                   return FALSE;
3785                 }
3786               break;
3787             }
3788           ok = bfd_set_section_contents (finfo->output_bfd, o, (void *) buf,
3789                                          (file_ptr) p->offset, size);
3790           free (buf);
3791           if (! ok)
3792             return FALSE;
3793         }
3794     }
3795   else
3796     {
3797 #ifdef MY_put_ext_reloc
3798       MY_put_ext_reloc (finfo->output_bfd, r_extern, r_index, p->offset,
3799                         howto, &erel, pr->addend);
3800 #else
3801       PUT_WORD (finfo->output_bfd, p->offset, erel.r_address);
3802
3803       if (bfd_header_big_endian (finfo->output_bfd))
3804         {
3805           erel.r_index[0] = r_index >> 16;
3806           erel.r_index[1] = r_index >> 8;
3807           erel.r_index[2] = r_index;
3808           erel.r_type[0] =
3809             ((r_extern ? RELOC_EXT_BITS_EXTERN_BIG : 0)
3810              | (howto->type << RELOC_EXT_BITS_TYPE_SH_BIG));
3811         }
3812       else
3813         {
3814           erel.r_index[2] = r_index >> 16;
3815           erel.r_index[1] = r_index >> 8;
3816           erel.r_index[0] = r_index;
3817           erel.r_type[0] =
3818             (r_extern ? RELOC_EXT_BITS_EXTERN_LITTLE : 0)
3819               | (howto->type << RELOC_EXT_BITS_TYPE_SH_LITTLE);
3820         }
3821
3822       PUT_WORD (finfo->output_bfd, (bfd_vma) pr->addend, erel.r_addend);
3823 #endif /* MY_put_ext_reloc */
3824
3825       rel_ptr = (void *) &erel;
3826     }
3827
3828   amt = obj_reloc_entry_size (finfo->output_bfd);
3829   if (bfd_seek (finfo->output_bfd, *reloff_ptr, SEEK_SET) != 0
3830       || bfd_bwrite (rel_ptr, amt, finfo->output_bfd) != amt)
3831     return FALSE;
3832
3833   *reloff_ptr += obj_reloc_entry_size (finfo->output_bfd);
3834
3835   /* Assert that the relocs have not run into the symbols, and that n
3836      the text relocs have not run into the data relocs.  */
3837   BFD_ASSERT (*reloff_ptr <= obj_sym_filepos (finfo->output_bfd)
3838               && (reloff_ptr != &finfo->treloff
3839                   || (*reloff_ptr
3840                       <= obj_datasec (finfo->output_bfd)->rel_filepos)));
3841
3842   return TRUE;
3843 }
3844
3845 /* Get the section corresponding to a reloc index.  */
3846
3847 static INLINE asection *
3848 aout_reloc_index_to_section (bfd *abfd, int indx)
3849 {
3850   switch (indx & N_TYPE)
3851     {
3852     case N_TEXT:   return obj_textsec (abfd);
3853     case N_DATA:   return obj_datasec (abfd);
3854     case N_BSS:    return obj_bsssec (abfd);
3855     case N_ABS:
3856     case N_UNDF:   return bfd_abs_section_ptr;
3857     default:       abort ();
3858     }
3859   return NULL;
3860 }
3861
3862 /* Relocate an a.out section using standard a.out relocs.  */
3863
3864 static bfd_boolean
3865 aout_link_input_section_std (struct aout_final_link_info *finfo,
3866                              bfd *input_bfd,
3867                              asection *input_section,
3868                              struct reloc_std_external *relocs,
3869                              bfd_size_type rel_size,
3870                              bfd_byte *contents)
3871 {
3872   bfd_boolean (*check_dynamic_reloc)
3873     (struct bfd_link_info *, bfd *, asection *,
3874              struct aout_link_hash_entry *, void *, bfd_byte *, bfd_boolean *,
3875              bfd_vma *);
3876   bfd *output_bfd;
3877   bfd_boolean relocatable;
3878   struct external_nlist *syms;
3879   char *strings;
3880   struct aout_link_hash_entry **sym_hashes;
3881   int *symbol_map;
3882   bfd_size_type reloc_count;
3883   struct reloc_std_external *rel;
3884   struct reloc_std_external *rel_end;
3885
3886   output_bfd = finfo->output_bfd;
3887   check_dynamic_reloc = aout_backend_info (output_bfd)->check_dynamic_reloc;
3888
3889   BFD_ASSERT (obj_reloc_entry_size (input_bfd) == RELOC_STD_SIZE);
3890   BFD_ASSERT (input_bfd->xvec->header_byteorder
3891               == output_bfd->xvec->header_byteorder);
3892
3893   relocatable = finfo->info->relocatable;
3894   syms = obj_aout_external_syms (input_bfd);
3895   strings = obj_aout_external_strings (input_bfd);
3896   sym_hashes = obj_aout_sym_hashes (input_bfd);
3897   symbol_map = finfo->symbol_map;
3898
3899   reloc_count = rel_size / RELOC_STD_SIZE;
3900   rel = relocs;
3901   rel_end = rel + reloc_count;
3902   for (; rel < rel_end; rel++)
3903     {
3904       bfd_vma r_addr;
3905       int r_index;
3906       int r_extern;
3907       int r_pcrel;
3908       int r_baserel = 0;
3909       reloc_howto_type *howto;
3910       struct aout_link_hash_entry *h = NULL;
3911       bfd_vma relocation;
3912       bfd_reloc_status_type r;
3913
3914       r_addr = GET_SWORD (input_bfd, rel->r_address);
3915
3916 #ifdef MY_reloc_howto
3917       howto = MY_reloc_howto (input_bfd, rel, r_index, r_extern, r_pcrel);
3918 #else
3919       {
3920         int r_jmptable;
3921         int r_relative;
3922         int r_length;
3923         unsigned int howto_idx;
3924
3925         if (bfd_header_big_endian (input_bfd))
3926           {
3927             r_index   =  (((unsigned int) rel->r_index[0] << 16)
3928                           | ((unsigned int) rel->r_index[1] << 8)
3929                           | rel->r_index[2]);
3930             r_extern  = (0 != (rel->r_type[0] & RELOC_STD_BITS_EXTERN_BIG));
3931             r_pcrel   = (0 != (rel->r_type[0] & RELOC_STD_BITS_PCREL_BIG));
3932             r_baserel = (0 != (rel->r_type[0] & RELOC_STD_BITS_BASEREL_BIG));
3933             r_jmptable= (0 != (rel->r_type[0] & RELOC_STD_BITS_JMPTABLE_BIG));
3934             r_relative= (0 != (rel->r_type[0] & RELOC_STD_BITS_RELATIVE_BIG));
3935             r_length  = ((rel->r_type[0] & RELOC_STD_BITS_LENGTH_BIG)
3936                          >> RELOC_STD_BITS_LENGTH_SH_BIG);
3937           }
3938         else
3939           {
3940             r_index   = (((unsigned int) rel->r_index[2] << 16)
3941                          | ((unsigned int) rel->r_index[1] << 8)
3942                          | rel->r_index[0]);
3943             r_extern  = (0 != (rel->r_type[0] & RELOC_STD_BITS_EXTERN_LITTLE));
3944             r_pcrel   = (0 != (rel->r_type[0] & RELOC_STD_BITS_PCREL_LITTLE));
3945             r_baserel = (0 != (rel->r_type[0]
3946                                & RELOC_STD_BITS_BASEREL_LITTLE));
3947             r_jmptable= (0 != (rel->r_type[0]
3948                                & RELOC_STD_BITS_JMPTABLE_LITTLE));
3949             r_relative= (0 != (rel->r_type[0]
3950                                & RELOC_STD_BITS_RELATIVE_LITTLE));
3951             r_length  = ((rel->r_type[0] & RELOC_STD_BITS_LENGTH_LITTLE)
3952                          >> RELOC_STD_BITS_LENGTH_SH_LITTLE);
3953           }
3954
3955         howto_idx = (r_length + 4 * r_pcrel + 8 * r_baserel
3956                      + 16 * r_jmptable + 32 * r_relative);
3957         BFD_ASSERT (howto_idx < TABLE_SIZE (howto_table_std));
3958         howto = howto_table_std + howto_idx;
3959       }
3960 #endif
3961
3962       if (relocatable)
3963         {
3964           /* We are generating a relocatable output file, and must
3965              modify the reloc accordingly.  */
3966           if (r_extern)
3967             {
3968               /* If we know the symbol this relocation is against,
3969                  convert it into a relocation against a section.  This
3970                  is what the native linker does.  */
3971               h = sym_hashes[r_index];
3972               if (h != NULL
3973                   && (h->root.type == bfd_link_hash_defined
3974                       || h->root.type == bfd_link_hash_defweak))
3975                 {
3976                   asection *output_section;
3977
3978                   /* Change the r_extern value.  */
3979                   if (bfd_header_big_endian (output_bfd))
3980                     rel->r_type[0] &=~ RELOC_STD_BITS_EXTERN_BIG;
3981                   else
3982                     rel->r_type[0] &=~ RELOC_STD_BITS_EXTERN_LITTLE;
3983
3984                   /* Compute a new r_index.  */
3985                   output_section = h->root.u.def.section->output_section;
3986                   if (output_section == obj_textsec (output_bfd))
3987                     r_index = N_TEXT;
3988                   else if (output_section == obj_datasec (output_bfd))
3989                     r_index = N_DATA;
3990                   else if (output_section == obj_bsssec (output_bfd))
3991                     r_index = N_BSS;
3992                   else
3993                     r_index = N_ABS;
3994
3995                   /* Add the symbol value and the section VMA to the
3996                      addend stored in the contents.  */
3997                   relocation = (h->root.u.def.value
3998                                 + output_section->vma
3999                                 + h->root.u.def.section->output_offset);
4000                 }
4001               else
4002                 {
4003                   /* We must change r_index according to the symbol
4004                      map.  */
4005                   r_index = symbol_map[r_index];
4006
4007                   if (r_index == -1)
4008                     {
4009                       if (h != NULL)
4010                         {
4011                           /* We decided to strip this symbol, but it
4012                              turns out that we can't.  Note that we
4013                              lose the other and desc information here.
4014                              I don't think that will ever matter for a
4015                              global symbol.  */
4016                           if (h->indx < 0)
4017                             {
4018                               h->indx = -2;
4019                               h->written = FALSE;
4020                               if (! aout_link_write_other_symbol (h,
4021                                                                   (void *) finfo))
4022                                 return FALSE;
4023                             }
4024                           r_index = h->indx;
4025                         }
4026                       else
4027                         {
4028                           const char *name;
4029
4030                           name = strings + GET_WORD (input_bfd,
4031                                                      syms[r_index].e_strx);
4032                           if (! ((*finfo->info->callbacks->unattached_reloc)
4033                                  (finfo->info, name, input_bfd, input_section,
4034                                   r_addr)))
4035                             return FALSE;
4036                           r_index = 0;
4037                         }
4038                     }
4039
4040                   relocation = 0;
4041                 }
4042
4043               /* Write out the new r_index value.  */
4044               if (bfd_header_big_endian (output_bfd))
4045                 {
4046                   rel->r_index[0] = r_index >> 16;
4047                   rel->r_index[1] = r_index >> 8;
4048                   rel->r_index[2] = r_index;
4049                 }
4050               else
4051                 {
4052                   rel->r_index[2] = r_index >> 16;
4053                   rel->r_index[1] = r_index >> 8;
4054                   rel->r_index[0] = r_index;
4055                 }
4056             }
4057           else
4058             {
4059               asection *section;
4060
4061               /* This is a relocation against a section.  We must
4062                  adjust by the amount that the section moved.  */
4063               section = aout_reloc_index_to_section (input_bfd, r_index);
4064               relocation = (section->output_section->vma
4065                             + section->output_offset
4066                             - section->vma);
4067             }
4068
4069           /* Change the address of the relocation.  */
4070           PUT_WORD (output_bfd,
4071                     r_addr + input_section->output_offset,
4072                     rel->r_address);
4073
4074           /* Adjust a PC relative relocation by removing the reference
4075              to the original address in the section and including the
4076              reference to the new address.  */
4077           if (r_pcrel)
4078             relocation -= (input_section->output_section->vma
4079                            + input_section->output_offset
4080                            - input_section->vma);
4081
4082 #ifdef MY_relocatable_reloc
4083           MY_relocatable_reloc (howto, output_bfd, rel, relocation, r_addr);
4084 #endif
4085
4086           if (relocation == 0)
4087             r = bfd_reloc_ok;
4088           else
4089             r = MY_relocate_contents (howto,
4090                                         input_bfd, relocation,
4091                                         contents + r_addr);
4092         }
4093       else
4094         {
4095           bfd_boolean hundef;
4096
4097           /* We are generating an executable, and must do a full
4098              relocation.  */
4099           hundef = FALSE;
4100
4101           if (r_extern)
4102             {
4103               h = sym_hashes[r_index];
4104
4105               if (h != NULL
4106                   && (h->root.type == bfd_link_hash_defined
4107                       || h->root.type == bfd_link_hash_defweak))
4108                 {
4109                   relocation = (h->root.u.def.value
4110                                 + h->root.u.def.section->output_section->vma
4111                                 + h->root.u.def.section->output_offset);
4112                 }
4113               else if (h != NULL
4114                        && h->root.type == bfd_link_hash_undefweak)
4115                 relocation = 0;
4116               else
4117                 {
4118                   hundef = TRUE;
4119                   relocation = 0;
4120                 }
4121             }
4122           else
4123             {
4124               asection *section;
4125
4126               section = aout_reloc_index_to_section (input_bfd, r_index);
4127               relocation = (section->output_section->vma
4128                             + section->output_offset
4129                             - section->vma);
4130               if (r_pcrel)
4131                 relocation += input_section->vma;
4132             }
4133
4134           if (check_dynamic_reloc != NULL)
4135             {
4136               bfd_boolean skip;
4137
4138               if (! ((*check_dynamic_reloc)
4139                      (finfo->info, input_bfd, input_section, h,
4140                       (void *) rel, contents, &skip, &relocation)))
4141                 return FALSE;
4142               if (skip)
4143                 continue;
4144             }
4145
4146           /* Now warn if a global symbol is undefined.  We could not
4147              do this earlier, because check_dynamic_reloc might want
4148              to skip this reloc.  */
4149           if (hundef && ! finfo->info->shared && ! r_baserel)
4150             {
4151               const char *name;
4152
4153               if (h != NULL)
4154                 name = h->root.root.string;
4155               else
4156                 name = strings + GET_WORD (input_bfd, syms[r_index].e_strx);
4157               if (! ((*finfo->info->callbacks->undefined_symbol)
4158                      (finfo->info, name, input_bfd, input_section,
4159                      r_addr, TRUE)))
4160                 return FALSE;
4161             }
4162
4163           r = MY_final_link_relocate (howto,
4164                                       input_bfd, input_section,
4165                                       contents, r_addr, relocation,
4166                                       (bfd_vma) 0);
4167         }
4168
4169       if (r != bfd_reloc_ok)
4170         {
4171           switch (r)
4172             {
4173             default:
4174             case bfd_reloc_outofrange:
4175               abort ();
4176             case bfd_reloc_overflow:
4177               {
4178                 const char *name;
4179
4180                 if (h != NULL)
4181                   name = NULL;
4182                 else if (r_extern)
4183                   name = strings + GET_WORD (input_bfd,
4184                                              syms[r_index].e_strx);
4185                 else
4186                   {
4187                     asection *s;
4188
4189                     s = aout_reloc_index_to_section (input_bfd, r_index);
4190                     name = bfd_section_name (input_bfd, s);
4191                   }
4192                 if (! ((*finfo->info->callbacks->reloc_overflow)
4193                        (finfo->info, (h ? &h->root : NULL), name,
4194                         howto->name, (bfd_vma) 0, input_bfd,
4195                         input_section, r_addr)))
4196                   return FALSE;
4197               }
4198               break;
4199             }
4200         }
4201     }
4202
4203   return TRUE;
4204 }
4205
4206 /* Relocate an a.out section using extended a.out relocs.  */
4207
4208 static bfd_boolean
4209 aout_link_input_section_ext (struct aout_final_link_info *finfo,
4210                              bfd *input_bfd,
4211                              asection *input_section,
4212                              struct reloc_ext_external *relocs,
4213                              bfd_size_type rel_size,
4214                              bfd_byte *contents)
4215 {
4216   bfd_boolean (*check_dynamic_reloc)
4217     (struct bfd_link_info *, bfd *, asection *,
4218              struct aout_link_hash_entry *, void *, bfd_byte *, bfd_boolean *,
4219              bfd_vma *);
4220   bfd *output_bfd;
4221   bfd_boolean relocatable;
4222   struct external_nlist *syms;
4223   char *strings;
4224   struct aout_link_hash_entry **sym_hashes;
4225   int *symbol_map;
4226   bfd_size_type reloc_count;
4227   struct reloc_ext_external *rel;
4228   struct reloc_ext_external *rel_end;
4229
4230   output_bfd = finfo->output_bfd;
4231   check_dynamic_reloc = aout_backend_info (output_bfd)->check_dynamic_reloc;
4232
4233   BFD_ASSERT (obj_reloc_entry_size (input_bfd) == RELOC_EXT_SIZE);
4234   BFD_ASSERT (input_bfd->xvec->header_byteorder
4235               == output_bfd->xvec->header_byteorder);
4236
4237   relocatable = finfo->info->relocatable;
4238   syms = obj_aout_external_syms (input_bfd);
4239   strings = obj_aout_external_strings (input_bfd);
4240   sym_hashes = obj_aout_sym_hashes (input_bfd);
4241   symbol_map = finfo->symbol_map;
4242
4243   reloc_count = rel_size / RELOC_EXT_SIZE;
4244   rel = relocs;
4245   rel_end = rel + reloc_count;
4246   for (; rel < rel_end; rel++)
4247     {
4248       bfd_vma r_addr;
4249       int r_index;
4250       int r_extern;
4251       unsigned int r_type;
4252       bfd_vma r_addend;
4253       struct aout_link_hash_entry *h = NULL;
4254       asection *r_section = NULL;
4255       bfd_vma relocation;
4256
4257       r_addr = GET_SWORD (input_bfd, rel->r_address);
4258
4259       if (bfd_header_big_endian (input_bfd))
4260         {
4261           r_index  = (((unsigned int) rel->r_index[0] << 16)
4262                       | ((unsigned int) rel->r_index[1] << 8)
4263                       | rel->r_index[2]);
4264           r_extern = (0 != (rel->r_type[0] & RELOC_EXT_BITS_EXTERN_BIG));
4265           r_type   = ((rel->r_type[0] & RELOC_EXT_BITS_TYPE_BIG)
4266                       >> RELOC_EXT_BITS_TYPE_SH_BIG);
4267         }
4268       else
4269         {
4270           r_index  = (((unsigned int) rel->r_index[2] << 16)
4271                       | ((unsigned int) rel->r_index[1] << 8)
4272                       | rel->r_index[0]);
4273           r_extern = (0 != (rel->r_type[0] & RELOC_EXT_BITS_EXTERN_LITTLE));
4274           r_type   = ((rel->r_type[0] & RELOC_EXT_BITS_TYPE_LITTLE)
4275                       >> RELOC_EXT_BITS_TYPE_SH_LITTLE);
4276         }
4277
4278       r_addend = GET_SWORD (input_bfd, rel->r_addend);
4279
4280       BFD_ASSERT (r_type < TABLE_SIZE (howto_table_ext));
4281
4282       if (relocatable)
4283         {
4284           /* We are generating a relocatable output file, and must
4285              modify the reloc accordingly.  */
4286           if (r_extern
4287               || r_type == (unsigned int) RELOC_BASE10
4288               || r_type == (unsigned int) RELOC_BASE13
4289               || r_type == (unsigned int) RELOC_BASE22)
4290             {
4291               /* If we know the symbol this relocation is against,
4292                  convert it into a relocation against a section.  This
4293                  is what the native linker does.  */
4294               if (r_type == (unsigned int) RELOC_BASE10
4295                   || r_type == (unsigned int) RELOC_BASE13
4296                   || r_type == (unsigned int) RELOC_BASE22)
4297                 h = NULL;
4298               else
4299                 h = sym_hashes[r_index];
4300               if (h != NULL
4301                   && (h->root.type == bfd_link_hash_defined
4302                       || h->root.type == bfd_link_hash_defweak))
4303                 {
4304                   asection *output_section;
4305
4306                   /* Change the r_extern value.  */
4307                   if (bfd_header_big_endian (output_bfd))
4308                     rel->r_type[0] &=~ RELOC_EXT_BITS_EXTERN_BIG;
4309                   else
4310                     rel->r_type[0] &=~ RELOC_EXT_BITS_EXTERN_LITTLE;
4311
4312                   /* Compute a new r_index.  */
4313                   output_section = h->root.u.def.section->output_section;
4314                   if (output_section == obj_textsec (output_bfd))
4315                     r_index = N_TEXT;
4316                   else if (output_section == obj_datasec (output_bfd))
4317                     r_index = N_DATA;
4318                   else if (output_section == obj_bsssec (output_bfd))
4319                     r_index = N_BSS;
4320                   else
4321                     r_index = N_ABS;
4322
4323                   /* Add the symbol value and the section VMA to the
4324                      addend.  */
4325                   relocation = (h->root.u.def.value
4326                                 + output_section->vma
4327                                 + h->root.u.def.section->output_offset);
4328
4329                   /* Now RELOCATION is the VMA of the final
4330                      destination.  If this is a PC relative reloc,
4331                      then ADDEND is the negative of the source VMA.
4332                      We want to set ADDEND to the difference between
4333                      the destination VMA and the source VMA, which
4334                      means we must adjust RELOCATION by the change in
4335                      the source VMA.  This is done below.  */
4336                 }
4337               else
4338                 {
4339                   /* We must change r_index according to the symbol
4340                      map.  */
4341                   r_index = symbol_map[r_index];
4342
4343                   if (r_index == -1)
4344                     {
4345                       if (h != NULL)
4346                         {
4347                           /* We decided to strip this symbol, but it
4348                              turns out that we can't.  Note that we
4349                              lose the other and desc information here.
4350                              I don't think that will ever matter for a
4351                              global symbol.  */
4352                           if (h->indx < 0)
4353                             {
4354                               h->indx = -2;
4355                               h->written = FALSE;
4356                               if (! aout_link_write_other_symbol (h,
4357                                                                   (void *) finfo))
4358                                 return FALSE;
4359                             }
4360                           r_index = h->indx;
4361                         }
4362                       else
4363                         {
4364                           const char *name;
4365
4366                           name = strings + GET_WORD (input_bfd,
4367                                                      syms[r_index].e_strx);
4368                           if (! ((*finfo->info->callbacks->unattached_reloc)
4369                                  (finfo->info, name, input_bfd, input_section,
4370                                   r_addr)))
4371                             return FALSE;
4372                           r_index = 0;
4373                         }
4374                     }
4375
4376                   relocation = 0;
4377
4378                   /* If this is a PC relative reloc, then the addend
4379                      is the negative of the source VMA.  We must
4380                      adjust it by the change in the source VMA.  This
4381                      is done below.  */
4382                 }
4383
4384               /* Write out the new r_index value.  */
4385               if (bfd_header_big_endian (output_bfd))
4386                 {
4387                   rel->r_index[0] = r_index >> 16;
4388                   rel->r_index[1] = r_index >> 8;
4389                   rel->r_index[2] = r_index;
4390                 }
4391               else
4392                 {
4393                   rel->r_index[2] = r_index >> 16;
4394                   rel->r_index[1] = r_index >> 8;
4395                   rel->r_index[0] = r_index;
4396                 }
4397             }
4398           else
4399             {
4400               /* This is a relocation against a section.  We must
4401                  adjust by the amount that the section moved.  */
4402               r_section = aout_reloc_index_to_section (input_bfd, r_index);
4403               relocation = (r_section->output_section->vma
4404                             + r_section->output_offset
4405                             - r_section->vma);
4406
4407               /* If this is a PC relative reloc, then the addend is
4408                  the difference in VMA between the destination and the
4409                  source.  We have just adjusted for the change in VMA
4410                  of the destination, so we must also adjust by the
4411                  change in VMA of the source.  This is done below.  */
4412             }
4413
4414           /* As described above, we must always adjust a PC relative
4415              reloc by the change in VMA of the source.  However, if
4416              pcrel_offset is set, then the addend does not include the
4417              location within the section, in which case we don't need
4418              to adjust anything.  */
4419           if (howto_table_ext[r_type].pc_relative
4420               && ! howto_table_ext[r_type].pcrel_offset)
4421             relocation -= (input_section->output_section->vma
4422                            + input_section->output_offset
4423                            - input_section->vma);
4424
4425           /* Change the addend if necessary.  */
4426           if (relocation != 0)
4427             PUT_WORD (output_bfd, r_addend + relocation, rel->r_addend);
4428
4429           /* Change the address of the relocation.  */
4430           PUT_WORD (output_bfd,
4431                     r_addr + input_section->output_offset,
4432                     rel->r_address);
4433         }
4434       else
4435         {
4436           bfd_boolean hundef;
4437           bfd_reloc_status_type r;
4438
4439           /* We are generating an executable, and must do a full
4440              relocation.  */
4441           hundef = FALSE;
4442
4443           if (r_extern)
4444             {
4445               h = sym_hashes[r_index];
4446
4447               if (h != NULL
4448                   && (h->root.type == bfd_link_hash_defined
4449                       || h->root.type == bfd_link_hash_defweak))
4450                 {
4451                   relocation = (h->root.u.def.value
4452                                 + h->root.u.def.section->output_section->vma
4453                                 + h->root.u.def.section->output_offset);
4454                 }
4455               else if (h != NULL
4456                        && h->root.type == bfd_link_hash_undefweak)
4457                 relocation = 0;
4458               else
4459                 {
4460                   hundef = TRUE;
4461                   relocation = 0;
4462                 }
4463             }
4464           else if (r_type == (unsigned int) RELOC_BASE10
4465                    || r_type == (unsigned int) RELOC_BASE13
4466                    || r_type == (unsigned int) RELOC_BASE22)
4467             {
4468               struct external_nlist *sym;
4469               int type;
4470
4471               /* For base relative relocs, r_index is always an index
4472                  into the symbol table, even if r_extern is 0.  */
4473               sym = syms + r_index;
4474               type = H_GET_8 (input_bfd, sym->e_type);
4475               if ((type & N_TYPE) == N_TEXT
4476                   || type == N_WEAKT)
4477                 r_section = obj_textsec (input_bfd);
4478               else if ((type & N_TYPE) == N_DATA
4479                        || type == N_WEAKD)
4480                 r_section = obj_datasec (input_bfd);
4481               else if ((type & N_TYPE) == N_BSS
4482                        || type == N_WEAKB)
4483                 r_section = obj_bsssec (input_bfd);
4484               else if ((type & N_TYPE) == N_ABS
4485                        || type == N_WEAKA)
4486                 r_section = bfd_abs_section_ptr;
4487               else
4488                 abort ();
4489               relocation = (r_section->output_section->vma
4490                             + r_section->output_offset
4491                             + (GET_WORD (input_bfd, sym->e_value)
4492                                - r_section->vma));
4493             }
4494           else
4495             {
4496               r_section = aout_reloc_index_to_section (input_bfd, r_index);
4497
4498               /* If this is a PC relative reloc, then R_ADDEND is the
4499                  difference between the two vmas, or
4500                    old_dest_sec + old_dest_off - (old_src_sec + old_src_off)
4501                  where
4502                    old_dest_sec == section->vma
4503                  and
4504                    old_src_sec == input_section->vma
4505                  and
4506                    old_src_off == r_addr
4507
4508                  _bfd_final_link_relocate expects RELOCATION +
4509                  R_ADDEND to be the VMA of the destination minus
4510                  r_addr (the minus r_addr is because this relocation
4511                  is not pcrel_offset, which is a bit confusing and
4512                  should, perhaps, be changed), or
4513                    new_dest_sec
4514                  where
4515                    new_dest_sec == output_section->vma + output_offset
4516                  We arrange for this to happen by setting RELOCATION to
4517                    new_dest_sec + old_src_sec - old_dest_sec
4518
4519                  If this is not a PC relative reloc, then R_ADDEND is
4520                  simply the VMA of the destination, so we set
4521                  RELOCATION to the change in the destination VMA, or
4522                    new_dest_sec - old_dest_sec
4523                  */
4524               relocation = (r_section->output_section->vma
4525                             + r_section->output_offset
4526                             - r_section->vma);
4527               if (howto_table_ext[r_type].pc_relative)
4528                 relocation += input_section->vma;
4529             }
4530
4531           if (check_dynamic_reloc != NULL)
4532             {
4533               bfd_boolean skip;
4534
4535               if (! ((*check_dynamic_reloc)
4536                      (finfo->info, input_bfd, input_section, h,
4537                       (void *) rel, contents, &skip, &relocation)))
4538                 return FALSE;
4539               if (skip)
4540                 continue;
4541             }
4542
4543           /* Now warn if a global symbol is undefined.  We could not
4544              do this earlier, because check_dynamic_reloc might want
4545              to skip this reloc.  */
4546           if (hundef
4547               && ! finfo->info->shared
4548               && r_type != (unsigned int) RELOC_BASE10
4549               && r_type != (unsigned int) RELOC_BASE13
4550               && r_type != (unsigned int) RELOC_BASE22)
4551             {
4552               const char *name;
4553
4554               if (h != NULL)
4555                 name = h->root.root.string;
4556               else
4557                 name = strings + GET_WORD (input_bfd, syms[r_index].e_strx);
4558               if (! ((*finfo->info->callbacks->undefined_symbol)
4559                      (finfo->info, name, input_bfd, input_section,
4560                      r_addr, TRUE)))
4561                 return FALSE;
4562             }
4563
4564           if (r_type != (unsigned int) RELOC_SPARC_REV32)
4565             r = MY_final_link_relocate (howto_table_ext + r_type,
4566                                         input_bfd, input_section,
4567                                         contents, r_addr, relocation,
4568                                         r_addend);
4569           else
4570             {
4571               bfd_vma x;
4572
4573               x = bfd_get_32 (input_bfd, contents + r_addr);
4574               x = x + relocation + r_addend;
4575               bfd_putl32 (/*input_bfd,*/ x, contents + r_addr);
4576               r = bfd_reloc_ok;
4577             }
4578
4579           if (r != bfd_reloc_ok)
4580             {
4581               switch (r)
4582                 {
4583                 default:
4584                 case bfd_reloc_outofrange:
4585                   abort ();
4586                 case bfd_reloc_overflow:
4587                   {
4588                     const char *name;
4589
4590                     if (h != NULL)
4591                       name = NULL;
4592                     else if (r_extern
4593                              || r_type == (unsigned int) RELOC_BASE10
4594                              || r_type == (unsigned int) RELOC_BASE13
4595                              || r_type == (unsigned int) RELOC_BASE22)
4596                       name = strings + GET_WORD (input_bfd,
4597                                                  syms[r_index].e_strx);
4598                     else
4599                       {
4600                         asection *s;
4601
4602                         s = aout_reloc_index_to_section (input_bfd, r_index);
4603                         name = bfd_section_name (input_bfd, s);
4604                       }
4605                     if (! ((*finfo->info->callbacks->reloc_overflow)
4606                            (finfo->info, (h ? &h->root : NULL), name,
4607                             howto_table_ext[r_type].name,
4608                             r_addend, input_bfd, input_section, r_addr)))
4609                       return FALSE;
4610                   }
4611                   break;
4612                 }
4613             }
4614         }
4615     }
4616
4617   return TRUE;
4618 }
4619
4620 /* Link an a.out section into the output file.  */
4621
4622 static bfd_boolean
4623 aout_link_input_section (struct aout_final_link_info *finfo,
4624                          bfd *input_bfd,
4625                          asection *input_section,
4626                          file_ptr *reloff_ptr,
4627                          bfd_size_type rel_size)
4628 {
4629   bfd_size_type input_size;
4630   void * relocs;
4631
4632   /* Get the section contents.  */
4633   input_size = input_section->size;
4634   if (! bfd_get_section_contents (input_bfd, input_section,
4635                                   (void *) finfo->contents,
4636                                   (file_ptr) 0, input_size))
4637     return FALSE;
4638
4639   /* Read in the relocs if we haven't already done it.  */
4640   if (aout_section_data (input_section) != NULL
4641       && aout_section_data (input_section)->relocs != NULL)
4642     relocs = aout_section_data (input_section)->relocs;
4643   else
4644     {
4645       relocs = finfo->relocs;
4646       if (rel_size > 0)
4647         {
4648           if (bfd_seek (input_bfd, input_section->rel_filepos, SEEK_SET) != 0
4649               || bfd_bread (relocs, rel_size, input_bfd) != rel_size)
4650             return FALSE;
4651         }
4652     }
4653
4654   /* Relocate the section contents.  */
4655   if (obj_reloc_entry_size (input_bfd) == RELOC_STD_SIZE)
4656     {
4657       if (! aout_link_input_section_std (finfo, input_bfd, input_section,
4658                                          (struct reloc_std_external *) relocs,
4659                                          rel_size, finfo->contents))
4660         return FALSE;
4661     }
4662   else
4663     {
4664       if (! aout_link_input_section_ext (finfo, input_bfd, input_section,
4665                                          (struct reloc_ext_external *) relocs,
4666                                          rel_size, finfo->contents))
4667         return FALSE;
4668     }
4669
4670   /* Write out the section contents.  */
4671   if (! bfd_set_section_contents (finfo->output_bfd,
4672                                   input_section->output_section,
4673                                   (void *) finfo->contents,
4674                                   (file_ptr) input_section->output_offset,
4675                                   input_size))
4676     return FALSE;
4677
4678   /* If we are producing relocatable output, the relocs were
4679      modified, and we now write them out.  */
4680   if (finfo->info->relocatable && rel_size > 0)
4681     {
4682       if (bfd_seek (finfo->output_bfd, *reloff_ptr, SEEK_SET) != 0)
4683         return FALSE;
4684       if (bfd_bwrite (relocs, rel_size, finfo->output_bfd) != rel_size)
4685         return FALSE;
4686       *reloff_ptr += rel_size;
4687
4688       /* Assert that the relocs have not run into the symbols, and
4689          that if these are the text relocs they have not run into the
4690          data relocs.  */
4691       BFD_ASSERT (*reloff_ptr <= obj_sym_filepos (finfo->output_bfd)
4692                   && (reloff_ptr != &finfo->treloff
4693                       || (*reloff_ptr
4694                           <= obj_datasec (finfo->output_bfd)->rel_filepos)));
4695     }
4696
4697   return TRUE;
4698 }
4699
4700 /* Adjust and write out the symbols for an a.out file.  Set the new
4701    symbol indices into a symbol_map.  */
4702
4703 static bfd_boolean
4704 aout_link_write_symbols (struct aout_final_link_info *finfo, bfd *input_bfd)
4705 {
4706   bfd *output_bfd;
4707   bfd_size_type sym_count;
4708   char *strings;
4709   enum bfd_link_strip strip;
4710   enum bfd_link_discard discard;
4711   struct external_nlist *outsym;
4712   bfd_size_type strtab_index;
4713   struct external_nlist *sym;
4714   struct external_nlist *sym_end;
4715   struct aout_link_hash_entry **sym_hash;
4716   int *symbol_map;
4717   bfd_boolean pass;
4718   bfd_boolean skip_next;
4719
4720   output_bfd = finfo->output_bfd;
4721   sym_count = obj_aout_external_sym_count (input_bfd);
4722   strings = obj_aout_external_strings (input_bfd);
4723   strip = finfo->info->strip;
4724   discard = finfo->info->discard;
4725   outsym = finfo->output_syms;
4726
4727   /* First write out a symbol for this object file, unless we are
4728      discarding such symbols.  */
4729   if (strip != strip_all
4730       && (strip != strip_some
4731           || bfd_hash_lookup (finfo->info->keep_hash, input_bfd->filename,
4732                               FALSE, FALSE) != NULL)
4733       && discard != discard_all)
4734     {
4735       H_PUT_8 (output_bfd, N_TEXT, outsym->e_type);
4736       H_PUT_8 (output_bfd, 0, outsym->e_other);
4737       H_PUT_16 (output_bfd, 0, outsym->e_desc);
4738       strtab_index = add_to_stringtab (output_bfd, finfo->strtab,
4739                                        input_bfd->filename, FALSE);
4740       if (strtab_index == (bfd_size_type) -1)
4741         return FALSE;
4742       PUT_WORD (output_bfd, strtab_index, outsym->e_strx);
4743       PUT_WORD (output_bfd,
4744                 (bfd_get_section_vma (output_bfd,
4745                                       obj_textsec (input_bfd)->output_section)
4746                  + obj_textsec (input_bfd)->output_offset),
4747                 outsym->e_value);
4748       ++obj_aout_external_sym_count (output_bfd);
4749       ++outsym;
4750     }
4751
4752   pass = FALSE;
4753   skip_next = FALSE;
4754   sym = obj_aout_external_syms (input_bfd);
4755   sym_end = sym + sym_count;
4756   sym_hash = obj_aout_sym_hashes (input_bfd);
4757   symbol_map = finfo->symbol_map;
4758   memset (symbol_map, 0, (size_t) sym_count * sizeof *symbol_map);
4759   for (; sym < sym_end; sym++, sym_hash++, symbol_map++)
4760     {
4761       const char *name;
4762       int type;
4763       struct aout_link_hash_entry *h;
4764       bfd_boolean skip;
4765       asection *symsec;
4766       bfd_vma val = 0;
4767       bfd_boolean copy;
4768
4769       /* We set *symbol_map to 0 above for all symbols.  If it has
4770          already been set to -1 for this symbol, it means that we are
4771          discarding it because it appears in a duplicate header file.
4772          See the N_BINCL code below.  */
4773       if (*symbol_map == -1)
4774         continue;
4775
4776       /* Initialize *symbol_map to -1, which means that the symbol was
4777          not copied into the output file.  We will change it later if
4778          we do copy the symbol over.  */
4779       *symbol_map = -1;
4780
4781       type = H_GET_8 (input_bfd, sym->e_type);
4782       name = strings + GET_WORD (input_bfd, sym->e_strx);
4783
4784       h = NULL;
4785
4786       if (pass)
4787         {
4788           /* Pass this symbol through.  It is the target of an
4789              indirect or warning symbol.  */
4790           val = GET_WORD (input_bfd, sym->e_value);
4791           pass = FALSE;
4792         }
4793       else if (skip_next)
4794         {
4795           /* Skip this symbol, which is the target of an indirect
4796              symbol that we have changed to no longer be an indirect
4797              symbol.  */
4798           skip_next = FALSE;
4799           continue;
4800         }
4801       else
4802         {
4803           struct aout_link_hash_entry *hresolve;
4804
4805           /* We have saved the hash table entry for this symbol, if
4806              there is one.  Note that we could just look it up again
4807              in the hash table, provided we first check that it is an
4808              external symbol.  */
4809           h = *sym_hash;
4810
4811           /* Use the name from the hash table, in case the symbol was
4812              wrapped.  */
4813           if (h != NULL
4814               && h->root.type != bfd_link_hash_warning)
4815             name = h->root.root.string;
4816
4817           /* If this is an indirect or warning symbol, then change
4818              hresolve to the base symbol.  We also change *sym_hash so
4819              that the relocation routines relocate against the real
4820              symbol.  */
4821           hresolve = h;
4822           if (h != (struct aout_link_hash_entry *) NULL
4823               && (h->root.type == bfd_link_hash_indirect
4824                   || h->root.type == bfd_link_hash_warning))
4825             {
4826               hresolve = (struct aout_link_hash_entry *) h->root.u.i.link;
4827               while (hresolve->root.type == bfd_link_hash_indirect
4828                      || hresolve->root.type == bfd_link_hash_warning)
4829                 hresolve = ((struct aout_link_hash_entry *)
4830                             hresolve->root.u.i.link);
4831               *sym_hash = hresolve;
4832             }
4833
4834           /* If the symbol has already been written out, skip it.  */
4835           if (h != NULL
4836               && h->written)
4837             {
4838               if ((type & N_TYPE) == N_INDR
4839                   || type == N_WARNING)
4840                 skip_next = TRUE;
4841               *symbol_map = h->indx;
4842               continue;
4843             }
4844
4845           /* See if we are stripping this symbol.  */
4846           skip = FALSE;
4847           switch (strip)
4848             {
4849             case strip_none:
4850               break;
4851             case strip_debugger:
4852               if ((type & N_STAB) != 0)
4853                 skip = TRUE;
4854               break;
4855             case strip_some:
4856               if (bfd_hash_lookup (finfo->info->keep_hash, name, FALSE, FALSE)
4857                   == NULL)
4858                 skip = TRUE;
4859               break;
4860             case strip_all:
4861               skip = TRUE;
4862               break;
4863             }
4864           if (skip)
4865             {
4866               if (h != NULL)
4867                 h->written = TRUE;
4868               continue;
4869             }
4870
4871           /* Get the value of the symbol.  */
4872           if ((type & N_TYPE) == N_TEXT
4873               || type == N_WEAKT)
4874             symsec = obj_textsec (input_bfd);
4875           else if ((type & N_TYPE) == N_DATA
4876                    || type == N_WEAKD)
4877             symsec = obj_datasec (input_bfd);
4878           else if ((type & N_TYPE) == N_BSS
4879                    || type == N_WEAKB)
4880             symsec = obj_bsssec (input_bfd);
4881           else if ((type & N_TYPE) == N_ABS
4882                    || type == N_WEAKA)
4883             symsec = bfd_abs_section_ptr;
4884           else if (((type & N_TYPE) == N_INDR
4885                     && (hresolve == NULL
4886                         || (hresolve->root.type != bfd_link_hash_defined
4887                             && hresolve->root.type != bfd_link_hash_defweak
4888                             && hresolve->root.type != bfd_link_hash_common)))
4889                    || type == N_WARNING)
4890             {
4891               /* Pass the next symbol through unchanged.  The
4892                  condition above for indirect symbols is so that if
4893                  the indirect symbol was defined, we output it with
4894                  the correct definition so the debugger will
4895                  understand it.  */
4896               pass = TRUE;
4897               val = GET_WORD (input_bfd, sym->e_value);
4898               symsec = NULL;
4899             }
4900           else if ((type & N_STAB) != 0)
4901             {
4902               val = GET_WORD (input_bfd, sym->e_value);
4903               symsec = NULL;
4904             }
4905           else
4906             {
4907               /* If we get here with an indirect symbol, it means that
4908                  we are outputting it with a real definition.  In such
4909                  a case we do not want to output the next symbol,
4910                  which is the target of the indirection.  */
4911               if ((type & N_TYPE) == N_INDR)
4912                 skip_next = TRUE;
4913
4914               symsec = NULL;
4915
4916               /* We need to get the value from the hash table.  We use
4917                  hresolve so that if we have defined an indirect
4918                  symbol we output the final definition.  */
4919               if (h == NULL)
4920                 {
4921                   switch (type & N_TYPE)
4922                     {
4923                     case N_SETT:
4924                       symsec = obj_textsec (input_bfd);
4925                       break;
4926                     case N_SETD:
4927                       symsec = obj_datasec (input_bfd);
4928                       break;
4929                     case N_SETB:
4930                       symsec = obj_bsssec (input_bfd);
4931                       break;
4932                     case N_SETA:
4933                       symsec = bfd_abs_section_ptr;
4934                       break;
4935                     default:
4936                       val = 0;
4937                       break;
4938                     }
4939                 }
4940               else if (hresolve->root.type == bfd_link_hash_defined
4941                        || hresolve->root.type == bfd_link_hash_defweak)
4942                 {
4943                   asection *input_section;
4944                   asection *output_section;
4945
4946                   /* This case usually means a common symbol which was
4947                      turned into a defined symbol.  */
4948                   input_section = hresolve->root.u.def.section;
4949                   output_section = input_section->output_section;
4950                   BFD_ASSERT (bfd_is_abs_section (output_section)
4951                               || output_section->owner == output_bfd);
4952                   val = (hresolve->root.u.def.value
4953                          + bfd_get_section_vma (output_bfd, output_section)
4954                          + input_section->output_offset);
4955
4956                   /* Get the correct type based on the section.  If
4957                      this is a constructed set, force it to be
4958                      globally visible.  */
4959                   if (type == N_SETT
4960                       || type == N_SETD
4961                       || type == N_SETB
4962                       || type == N_SETA)
4963                     type |= N_EXT;
4964
4965                   type &=~ N_TYPE;
4966
4967                   if (output_section == obj_textsec (output_bfd))
4968                     type |= (hresolve->root.type == bfd_link_hash_defined
4969                              ? N_TEXT
4970                              : N_WEAKT);
4971                   else if (output_section == obj_datasec (output_bfd))
4972                     type |= (hresolve->root.type == bfd_link_hash_defined
4973                              ? N_DATA
4974                              : N_WEAKD);
4975                   else if (output_section == obj_bsssec (output_bfd))
4976                     type |= (hresolve->root.type == bfd_link_hash_defined
4977                              ? N_BSS
4978                              : N_WEAKB);
4979                   else
4980                     type |= (hresolve->root.type == bfd_link_hash_defined
4981                              ? N_ABS
4982                              : N_WEAKA);
4983                 }
4984               else if (hresolve->root.type == bfd_link_hash_common)
4985                 val = hresolve->root.u.c.size;
4986               else if (hresolve->root.type == bfd_link_hash_undefweak)
4987                 {
4988                   val = 0;
4989                   type = N_WEAKU;
4990                 }
4991               else
4992                 val = 0;
4993             }
4994           if (symsec != NULL)
4995             val = (symsec->output_section->vma
4996                    + symsec->output_offset
4997                    + (GET_WORD (input_bfd, sym->e_value)
4998                       - symsec->vma));
4999
5000           /* If this is a global symbol set the written flag, and if
5001              it is a local symbol see if we should discard it.  */
5002           if (h != NULL)
5003             {
5004               h->written = TRUE;
5005               h->indx = obj_aout_external_sym_count (output_bfd);
5006             }
5007           else if ((type & N_TYPE) != N_SETT
5008                    && (type & N_TYPE) != N_SETD
5009                    && (type & N_TYPE) != N_SETB
5010                    && (type & N_TYPE) != N_SETA)
5011             {
5012               switch (discard)
5013                 {
5014                 case discard_none:
5015                 case discard_sec_merge:
5016                   break;
5017                 case discard_l:
5018                   if ((type & N_STAB) == 0
5019                       && bfd_is_local_label_name (input_bfd, name))
5020                     skip = TRUE;
5021                   break;
5022                 case discard_all:
5023                   skip = TRUE;
5024                   break;
5025                 }
5026               if (skip)
5027                 {
5028                   pass = FALSE;
5029                   continue;
5030                 }
5031             }
5032
5033           /* An N_BINCL symbol indicates the start of the stabs
5034              entries for a header file.  We need to scan ahead to the
5035              next N_EINCL symbol, ignoring nesting, adding up all the
5036              characters in the symbol names, not including the file
5037              numbers in types (the first number after an open
5038              parenthesis).  */
5039           if (type == (int) N_BINCL)
5040             {
5041               struct external_nlist *incl_sym;
5042               int nest;
5043               struct aout_link_includes_entry *incl_entry;
5044               struct aout_link_includes_totals *t;
5045
5046               val = 0;
5047               nest = 0;
5048               for (incl_sym = sym + 1; incl_sym < sym_end; incl_sym++)
5049                 {
5050                   int incl_type;
5051
5052                   incl_type = H_GET_8 (input_bfd, incl_sym->e_type);
5053                   if (incl_type == (int) N_EINCL)
5054                     {
5055                       if (nest == 0)
5056                         break;
5057                       --nest;
5058                     }
5059                   else if (incl_type == (int) N_BINCL)
5060                     ++nest;
5061                   else if (nest == 0)
5062                     {
5063                       const char *s;
5064
5065                       s = strings + GET_WORD (input_bfd, incl_sym->e_strx);
5066                       for (; *s != '\0'; s++)
5067                         {
5068                           val += *s;
5069                           if (*s == '(')
5070                             {
5071                               /* Skip the file number.  */
5072                               ++s;
5073                               while (ISDIGIT (*s))
5074                                 ++s;
5075                               --s;
5076                             }
5077                         }
5078                     }
5079                 }
5080
5081               /* If we have already included a header file with the
5082                  same value, then replace this one with an N_EXCL
5083                  symbol.  */
5084               copy = (bfd_boolean) (! finfo->info->keep_memory);
5085               incl_entry = aout_link_includes_lookup (&finfo->includes,
5086                                                       name, TRUE, copy);
5087               if (incl_entry == NULL)
5088                 return FALSE;
5089               for (t = incl_entry->totals; t != NULL; t = t->next)
5090                 if (t->total == val)
5091                   break;
5092               if (t == NULL)
5093                 {
5094                   /* This is the first time we have seen this header
5095                      file with this set of stabs strings.  */
5096                   t = bfd_hash_allocate (&finfo->includes.root,
5097                                          sizeof *t);
5098                   if (t == NULL)
5099                     return FALSE;
5100                   t->total = val;
5101                   t->next = incl_entry->totals;
5102                   incl_entry->totals = t;
5103                 }
5104               else
5105                 {
5106                   int *incl_map;
5107
5108                   /* This is a duplicate header file.  We must change
5109                      it to be an N_EXCL entry, and mark all the
5110                      included symbols to prevent outputting them.  */
5111                   type = (int) N_EXCL;
5112
5113                   nest = 0;
5114                   for (incl_sym = sym + 1, incl_map = symbol_map + 1;
5115                        incl_sym < sym_end;
5116                        incl_sym++, incl_map++)
5117                     {
5118                       int incl_type;
5119
5120                       incl_type = H_GET_8 (input_bfd, incl_sym->e_type);
5121                       if (incl_type == (int) N_EINCL)
5122                         {
5123                           if (nest == 0)
5124                             {
5125                               *incl_map = -1;
5126                               break;
5127                             }
5128                           --nest;
5129                         }
5130                       else if (incl_type == (int) N_BINCL)
5131                         ++nest;
5132                       else if (nest == 0)
5133                         *incl_map = -1;
5134                     }
5135                 }
5136             }
5137         }
5138
5139       /* Copy this symbol into the list of symbols we are going to
5140          write out.  */
5141       H_PUT_8 (output_bfd, type, outsym->e_type);
5142       H_PUT_8 (output_bfd, H_GET_8 (input_bfd, sym->e_other), outsym->e_other);
5143       H_PUT_16 (output_bfd, H_GET_16 (input_bfd, sym->e_desc), outsym->e_desc);
5144       copy = FALSE;
5145       if (! finfo->info->keep_memory)
5146         {
5147           /* name points into a string table which we are going to
5148              free.  If there is a hash table entry, use that string.
5149              Otherwise, copy name into memory.  */
5150           if (h != NULL)
5151             name = h->root.root.string;
5152           else
5153             copy = TRUE;
5154         }
5155       strtab_index = add_to_stringtab (output_bfd, finfo->strtab,
5156                                        name, copy);
5157       if (strtab_index == (bfd_size_type) -1)
5158         return FALSE;
5159       PUT_WORD (output_bfd, strtab_index, outsym->e_strx);
5160       PUT_WORD (output_bfd, val, outsym->e_value);
5161       *symbol_map = obj_aout_external_sym_count (output_bfd);
5162       ++obj_aout_external_sym_count (output_bfd);
5163       ++outsym;
5164     }
5165
5166   /* Write out the output symbols we have just constructed.  */
5167   if (outsym > finfo->output_syms)
5168     {
5169       bfd_size_type outsym_size;
5170
5171       if (bfd_seek (output_bfd, finfo->symoff, SEEK_SET) != 0)
5172         return FALSE;
5173       outsym_size = outsym - finfo->output_syms;
5174       outsym_size *= EXTERNAL_NLIST_SIZE;
5175       if (bfd_bwrite ((void *) finfo->output_syms, outsym_size, output_bfd)
5176           != outsym_size)
5177         return FALSE;
5178       finfo->symoff += outsym_size;
5179     }
5180
5181   return TRUE;
5182 }
5183
5184 /* Link an a.out input BFD into the output file.  */
5185
5186 static bfd_boolean
5187 aout_link_input_bfd (struct aout_final_link_info *finfo, bfd *input_bfd)
5188 {
5189   bfd_size_type sym_count;
5190
5191   BFD_ASSERT (bfd_get_format (input_bfd) == bfd_object);
5192
5193   /* If this is a dynamic object, it may need special handling.  */
5194   if ((input_bfd->flags & DYNAMIC) != 0
5195       && aout_backend_info (input_bfd)->link_dynamic_object != NULL)
5196     return ((*aout_backend_info (input_bfd)->link_dynamic_object)
5197             (finfo->info, input_bfd));
5198
5199   /* Get the symbols.  We probably have them already, unless
5200      finfo->info->keep_memory is FALSE.  */
5201   if (! aout_get_external_symbols (input_bfd))
5202     return FALSE;
5203
5204   sym_count = obj_aout_external_sym_count (input_bfd);
5205
5206   /* Write out the symbols and get a map of the new indices.  The map
5207      is placed into finfo->symbol_map.  */
5208   if (! aout_link_write_symbols (finfo, input_bfd))
5209     return FALSE;
5210
5211   /* Relocate and write out the sections.  These functions use the
5212      symbol map created by aout_link_write_symbols.  The linker_mark
5213      field will be set if these sections are to be included in the
5214      link, which will normally be the case.  */
5215   if (obj_textsec (input_bfd)->linker_mark)
5216     {
5217       if (! aout_link_input_section (finfo, input_bfd,
5218                                      obj_textsec (input_bfd),
5219                                      &finfo->treloff,
5220                                      exec_hdr (input_bfd)->a_trsize))
5221         return FALSE;
5222     }
5223   if (obj_datasec (input_bfd)->linker_mark)
5224     {
5225       if (! aout_link_input_section (finfo, input_bfd,
5226                                      obj_datasec (input_bfd),
5227                                      &finfo->dreloff,
5228                                      exec_hdr (input_bfd)->a_drsize))
5229         return FALSE;
5230     }
5231
5232   /* If we are not keeping memory, we don't need the symbols any
5233      longer.  We still need them if we are keeping memory, because the
5234      strings in the hash table point into them.  */
5235   if (! finfo->info->keep_memory)
5236     {
5237       if (! aout_link_free_symbols (input_bfd))
5238         return FALSE;
5239     }
5240
5241   return TRUE;
5242 }
5243
5244 /* Do the final link step.  This is called on the output BFD.  The
5245    INFO structure should point to a list of BFDs linked through the
5246    link_next field which can be used to find each BFD which takes part
5247    in the output.  Also, each section in ABFD should point to a list
5248    of bfd_link_order structures which list all the input sections for
5249    the output section.  */
5250
5251 bfd_boolean
5252 NAME (aout, final_link) (bfd *abfd,
5253                          struct bfd_link_info *info,
5254                          void (*callback) (bfd *, file_ptr *, file_ptr *, file_ptr *))
5255 {
5256   struct aout_final_link_info aout_info;
5257   bfd_boolean includes_hash_initialized = FALSE;
5258   bfd *sub;
5259   bfd_size_type trsize, drsize;
5260   bfd_size_type max_contents_size;
5261   bfd_size_type max_relocs_size;
5262   bfd_size_type max_sym_count;
5263   bfd_size_type text_size;
5264   file_ptr text_end;
5265   struct bfd_link_order *p;
5266   asection *o;
5267   bfd_boolean have_link_order_relocs;
5268
5269   if (info->shared)
5270     abfd->flags |= DYNAMIC;
5271
5272   aout_info.info = info;
5273   aout_info.output_bfd = abfd;
5274   aout_info.contents = NULL;
5275   aout_info.relocs = NULL;
5276   aout_info.symbol_map = NULL;
5277   aout_info.output_syms = NULL;
5278
5279   if (!bfd_hash_table_init_n (&aout_info.includes.root,
5280                               aout_link_includes_newfunc,
5281                               sizeof (struct aout_link_includes_entry),
5282                               251))
5283     goto error_return;
5284   includes_hash_initialized = TRUE;
5285
5286   /* Figure out the largest section size.  Also, if generating
5287      relocatable output, count the relocs.  */
5288   trsize = 0;
5289   drsize = 0;
5290   max_contents_size = 0;
5291   max_relocs_size = 0;
5292   max_sym_count = 0;
5293   for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
5294     {
5295       bfd_size_type sz;
5296
5297       if (info->relocatable)
5298         {
5299           if (bfd_get_flavour (sub) == bfd_target_aout_flavour)
5300             {
5301               trsize += exec_hdr (sub)->a_trsize;
5302               drsize += exec_hdr (sub)->a_drsize;
5303             }
5304           else
5305             {
5306               /* FIXME: We need to identify the .text and .data sections
5307                  and call get_reloc_upper_bound and canonicalize_reloc to
5308                  work out the number of relocs needed, and then multiply
5309                  by the reloc size.  */
5310               (*_bfd_error_handler)
5311                 (_("%s: relocatable link from %s to %s not supported"),
5312                  bfd_get_filename (abfd),
5313                  sub->xvec->name, abfd->xvec->name);
5314               bfd_set_error (bfd_error_invalid_operation);
5315               goto error_return;
5316             }
5317         }
5318
5319       if (bfd_get_flavour (sub) == bfd_target_aout_flavour)
5320         {
5321           sz = obj_textsec (sub)->size;
5322           if (sz > max_contents_size)
5323             max_contents_size = sz;
5324           sz = obj_datasec (sub)->size;
5325           if (sz > max_contents_size)
5326             max_contents_size = sz;
5327
5328           sz = exec_hdr (sub)->a_trsize;
5329           if (sz > max_relocs_size)
5330             max_relocs_size = sz;
5331           sz = exec_hdr (sub)->a_drsize;
5332           if (sz > max_relocs_size)
5333             max_relocs_size = sz;
5334
5335           sz = obj_aout_external_sym_count (sub);
5336           if (sz > max_sym_count)
5337             max_sym_count = sz;
5338         }
5339     }
5340
5341   if (info->relocatable)
5342     {
5343       if (obj_textsec (abfd) != NULL)
5344         trsize += (_bfd_count_link_order_relocs (obj_textsec (abfd)
5345                                                  ->map_head.link_order)
5346                    * obj_reloc_entry_size (abfd));
5347       if (obj_datasec (abfd) != NULL)
5348         drsize += (_bfd_count_link_order_relocs (obj_datasec (abfd)
5349                                                  ->map_head.link_order)
5350                    * obj_reloc_entry_size (abfd));
5351     }
5352
5353   exec_hdr (abfd)->a_trsize = trsize;
5354   exec_hdr (abfd)->a_drsize = drsize;
5355
5356   exec_hdr (abfd)->a_entry = bfd_get_start_address (abfd);
5357
5358   /* Adjust the section sizes and vmas according to the magic number.
5359      This sets a_text, a_data and a_bss in the exec_hdr and sets the
5360      filepos for each section.  */
5361   if (! NAME (aout, adjust_sizes_and_vmas) (abfd, &text_size, &text_end))
5362     goto error_return;
5363
5364   /* The relocation and symbol file positions differ among a.out
5365      targets.  We are passed a callback routine from the backend
5366      specific code to handle this.
5367      FIXME: At this point we do not know how much space the symbol
5368      table will require.  This will not work for any (nonstandard)
5369      a.out target that needs to know the symbol table size before it
5370      can compute the relocation file positions.  This may or may not
5371      be the case for the hp300hpux target, for example.  */
5372   (*callback) (abfd, &aout_info.treloff, &aout_info.dreloff,
5373                &aout_info.symoff);
5374   obj_textsec (abfd)->rel_filepos = aout_info.treloff;
5375   obj_datasec (abfd)->rel_filepos = aout_info.dreloff;
5376   obj_sym_filepos (abfd) = aout_info.symoff;
5377
5378   /* We keep a count of the symbols as we output them.  */
5379   obj_aout_external_sym_count (abfd) = 0;
5380
5381   /* We accumulate the string table as we write out the symbols.  */
5382   aout_info.strtab = _bfd_stringtab_init ();
5383   if (aout_info.strtab == NULL)
5384     goto error_return;
5385
5386   /* Allocate buffers to hold section contents and relocs.  */
5387   aout_info.contents = bfd_malloc (max_contents_size);
5388   aout_info.relocs = bfd_malloc (max_relocs_size);
5389   aout_info.symbol_map = bfd_malloc (max_sym_count * sizeof (int *));
5390   aout_info.output_syms = bfd_malloc ((max_sym_count + 1)
5391                                       * sizeof (struct external_nlist));
5392   if ((aout_info.contents == NULL && max_contents_size != 0)
5393       || (aout_info.relocs == NULL && max_relocs_size != 0)
5394       || (aout_info.symbol_map == NULL && max_sym_count != 0)
5395       || aout_info.output_syms == NULL)
5396     goto error_return;
5397
5398   /* If we have a symbol named __DYNAMIC, force it out now.  This is
5399      required by SunOS.  Doing this here rather than in sunos.c is a
5400      hack, but it's easier than exporting everything which would be
5401      needed.  */
5402   {
5403     struct aout_link_hash_entry *h;
5404
5405     h = aout_link_hash_lookup (aout_hash_table (info), "__DYNAMIC",
5406                                FALSE, FALSE, FALSE);
5407     if (h != NULL)
5408       aout_link_write_other_symbol (h, &aout_info);
5409   }
5410
5411   /* The most time efficient way to do the link would be to read all
5412      the input object files into memory and then sort out the
5413      information into the output file.  Unfortunately, that will
5414      probably use too much memory.  Another method would be to step
5415      through everything that composes the text section and write it
5416      out, and then everything that composes the data section and write
5417      it out, and then write out the relocs, and then write out the
5418      symbols.  Unfortunately, that requires reading stuff from each
5419      input file several times, and we will not be able to keep all the
5420      input files open simultaneously, and reopening them will be slow.
5421
5422      What we do is basically process one input file at a time.  We do
5423      everything we need to do with an input file once--copy over the
5424      section contents, handle the relocation information, and write
5425      out the symbols--and then we throw away the information we read
5426      from it.  This approach requires a lot of lseeks of the output
5427      file, which is unfortunate but still faster than reopening a lot
5428      of files.
5429
5430      We use the output_has_begun field of the input BFDs to see
5431      whether we have already handled it.  */
5432   for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
5433     sub->output_has_begun = FALSE;
5434
5435   /* Mark all sections which are to be included in the link.  This
5436      will normally be every section.  We need to do this so that we
5437      can identify any sections which the linker has decided to not
5438      include.  */
5439   for (o = abfd->sections; o != NULL; o = o->next)
5440     {
5441       for (p = o->map_head.link_order; p != NULL; p = p->next)
5442         if (p->type == bfd_indirect_link_order)
5443           p->u.indirect.section->linker_mark = TRUE;
5444     }
5445
5446   have_link_order_relocs = FALSE;
5447   for (o = abfd->sections; o != NULL; o = o->next)
5448     {
5449       for (p = o->map_head.link_order;
5450            p != NULL;
5451            p = p->next)
5452         {
5453           if (p->type == bfd_indirect_link_order
5454               && (bfd_get_flavour (p->u.indirect.section->owner)
5455                   == bfd_target_aout_flavour))
5456             {
5457               bfd *input_bfd;
5458
5459               input_bfd = p->u.indirect.section->owner;
5460               if (! input_bfd->output_has_begun)
5461                 {
5462                   if (! aout_link_input_bfd (&aout_info, input_bfd))
5463                     goto error_return;
5464                   input_bfd->output_has_begun = TRUE;
5465                 }
5466             }
5467           else if (p->type == bfd_section_reloc_link_order
5468                    || p->type == bfd_symbol_reloc_link_order)
5469             {
5470               /* These are handled below.  */
5471               have_link_order_relocs = TRUE;
5472             }
5473           else
5474             {
5475               if (! _bfd_default_link_order (abfd, info, o, p))
5476                 goto error_return;
5477             }
5478         }
5479     }
5480
5481   /* Write out any symbols that we have not already written out.  */
5482   aout_link_hash_traverse (aout_hash_table (info),
5483                            aout_link_write_other_symbol,
5484                            (void *) &aout_info);
5485
5486   /* Now handle any relocs we were asked to create by the linker.
5487      These did not come from any input file.  We must do these after
5488      we have written out all the symbols, so that we know the symbol
5489      indices to use.  */
5490   if (have_link_order_relocs)
5491     {
5492       for (o = abfd->sections; o != NULL; o = o->next)
5493         {
5494           for (p = o->map_head.link_order;
5495                p != NULL;
5496                p = p->next)
5497             {
5498               if (p->type == bfd_section_reloc_link_order
5499                   || p->type == bfd_symbol_reloc_link_order)
5500                 {
5501                   if (! aout_link_reloc_link_order (&aout_info, o, p))
5502                     goto error_return;
5503                 }
5504             }
5505         }
5506     }
5507
5508   if (aout_info.contents != NULL)
5509     {
5510       free (aout_info.contents);
5511       aout_info.contents = NULL;
5512     }
5513   if (aout_info.relocs != NULL)
5514     {
5515       free (aout_info.relocs);
5516       aout_info.relocs = NULL;
5517     }
5518   if (aout_info.symbol_map != NULL)
5519     {
5520       free (aout_info.symbol_map);
5521       aout_info.symbol_map = NULL;
5522     }
5523   if (aout_info.output_syms != NULL)
5524     {
5525       free (aout_info.output_syms);
5526       aout_info.output_syms = NULL;
5527     }
5528   if (includes_hash_initialized)
5529     {
5530       bfd_hash_table_free (&aout_info.includes.root);
5531       includes_hash_initialized = FALSE;
5532     }
5533
5534   /* Finish up any dynamic linking we may be doing.  */
5535   if (aout_backend_info (abfd)->finish_dynamic_link != NULL)
5536     {
5537       if (! (*aout_backend_info (abfd)->finish_dynamic_link) (abfd, info))
5538         goto error_return;
5539     }
5540
5541   /* Update the header information.  */
5542   abfd->symcount = obj_aout_external_sym_count (abfd);
5543   exec_hdr (abfd)->a_syms = abfd->symcount * EXTERNAL_NLIST_SIZE;
5544   obj_str_filepos (abfd) = obj_sym_filepos (abfd) + exec_hdr (abfd)->a_syms;
5545   obj_textsec (abfd)->reloc_count =
5546     exec_hdr (abfd)->a_trsize / obj_reloc_entry_size (abfd);
5547   obj_datasec (abfd)->reloc_count =
5548     exec_hdr (abfd)->a_drsize / obj_reloc_entry_size (abfd);
5549
5550   /* Write out the string table, unless there are no symbols.  */
5551   if (abfd->symcount > 0)
5552     {
5553       if (bfd_seek (abfd, obj_str_filepos (abfd), SEEK_SET) != 0
5554           || ! emit_stringtab (abfd, aout_info.strtab))
5555         goto error_return;
5556     }
5557   else if (obj_textsec (abfd)->reloc_count == 0
5558            && obj_datasec (abfd)->reloc_count == 0)
5559     {
5560       bfd_byte b;
5561       file_ptr pos;
5562
5563       b = 0;
5564       pos = obj_datasec (abfd)->filepos + exec_hdr (abfd)->a_data - 1;
5565       if (bfd_seek (abfd, pos, SEEK_SET) != 0
5566           || bfd_bwrite (&b, (bfd_size_type) 1, abfd) != 1)
5567         goto error_return;
5568     }
5569
5570   return TRUE;
5571
5572  error_return:
5573   if (aout_info.contents != NULL)
5574     free (aout_info.contents);
5575   if (aout_info.relocs != NULL)
5576     free (aout_info.relocs);
5577   if (aout_info.symbol_map != NULL)
5578     free (aout_info.symbol_map);
5579   if (aout_info.output_syms != NULL)
5580     free (aout_info.output_syms);
5581   if (includes_hash_initialized)
5582     bfd_hash_table_free (&aout_info.includes.root);
5583   return FALSE;
5584 }