OSDN Git Service

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