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