OSDN Git Service

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