RS/6000 support, by Metin G. Ozisik, Mimi Phûông-Thåo Võ, and John Gilmore.
[platform/upstream/binutils.git] / bfd / coffcode.h
1 /* Support for Intel 960 COFF and Motorola 88k BCS COFF (and maybe others)
2    Copyright (C) 1990-1991 Free Software Foundation, Inc.
3    Written by Cygnus Support.
4
5 This file is part of BFD, the Binary File Descriptor library.
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.  */
20
21 /*doc*
22 @section coff backends
23
24 BFD supports a number of different flavours of coff format. The major
25 difference between formats are the sizes and alignments of fields in
26 structures on disk, and the occasional extra field.
27
28 Coff in all its varieties is implimented with a few common files and a
29 number of implementation specific files. For example, The 88k bcs coff
30 format is implemented in the file @code{m88k-bcs.c}. This file
31 @code{#include}s @code{m88k-bcs.h} which defines the external
32 structure of the coff format for the 88k, and @code{internalcoff.h}
33 which defines the internal structure. @code{m88k-bcs.c} also defines
34 the relocations used by the 88k format @xref{Relocations}. Then the
35 major portion of coff code is included (@code{coffcode.h}) which
36 defines the methods used to act upon the types defined in
37 @code{m88k-bcs.h} and @code{internalcoff.h}.
38
39 The Intel i960 processor version of coff is implemented in
40 @code{icoff.c}. This file has the same structure as
41 @code{m88k-bcs.c}, except that it includes @code{intel-coff.h} rather
42 than @code{m88k-bcs.h}.
43
44 @subsection Porting To A New Version of Coff
45
46 The recommended method is to select from the existing implimentations
47 the version of coff which is most like the one you want to use, for
48 our purposes, we'll say that i386 coff is the one you select, and that
49 your coff flavour is called foo. Copy the @code{i386coff.c} to @code{foocoff.c},
50 copy @code{../include/i386coff.h} to @code{../include/foocoff.h} and
51 add the lines to @code{targets.c} and @code{Makefile.in} so that your
52 new back end is used.
53
54 Alter the shapes of the structures in @code{../include/foocoff.h} so
55 that they match what you need. You will probably also have to add
56 @code{#ifdef}s to the code in @code{internalcoff.h} and
57 @code{coffcode.h} if your version of coff is too wild.
58
59 You can verify that your new BFD backend works quite simply by
60 building @code{objdump} from the @code{binutils} directory, and
61 making sure that its version of what's going on at your host systems
62 idea (assuming it has the pretty standard coff dump utility (usually
63 called @code{att-dump} or just @code{dump})) are the same.
64
65 Then clean up your code, and send what you've done to Cygnus. Then your stuff
66 will be in the next release, and you won't have to keep integrating
67 it.
68
69 @subsection How The Coff Backend Works
70
71 @subsubsection Bit Twiddling
72 Each flavour of coff supported in BFD has its own header file
73 descibing the external layout of the structures. There is also an
74 internal description of the coff layout (in @code{internalcoff.h})
75 file (@code{}). A major function of the coff backend is swapping the
76 bytes and twiddling the bits to translate the external form of the
77 structures into the normal internal form. This is all performed in the
78 @code{bfd_swap}_@i{thing}_@i{direction} routines. Some elements are
79 different sizes between different versions of coff, it is the duty of
80 the coff version specific include file to override the definitions of
81 various packing routines in @code{coffcode.h}. Eg the size of line
82 number entry in coff is sometimes 16 bits, and sometimes 32 bits.
83 @code{#define}ing @code{PUT_LNSZ_LNNO} and @code{GET_LNSZ_LNNO} will
84 select the correct one. No doubt, some day someone will find a version
85 of coff which has a varying field size not catered for at the moment.
86 To port BFD, that person will have to add more @code{#defines}.
87
88 Three of the bit twiddling routines are exported to @code{gdb};
89 @code{coff_swap_aux_in}, @code{coff_swap_sym_in} and
90 @code{coff_swap_linno_in}. @code{GDB} reads the symbol table on its
91 own, but uses BFD to fix things up.
92
93 More of the bit twiddlers are exported for @code{gas};
94 @code{coff_swap_aux_out}, @code{coff_swap_sym_out},
95 @code{coff_swap_lineno_out}, @code{coff_swap_reloc_out},
96 @code{coff_swap_filehdr_out}, @code{coff_swap_aouthdr_out},
97 @code{coff_swap_scnhdr_out}. @code{Gas} currently keeps track of all
98 the symbol table and reloc drudgery itself, thereby saving the
99 internal BFD overhead, but uses BFD to swap things on the way out,
100 making cross ports much safer.  This also allows BFD (and thus the
101 linker) to use the same header files as @code{gas}, which makes one
102 avenue to disaster disappear.
103
104 @subsubsection Symbol Reading
105 The simple canonical form for symbols used by BFD is not rich enough
106 to keep all the information available in a coff symbol table. The back
107 end gets around this by keeping the original symbol table around,
108 "behind the scenes".
109
110 When a symbol table is requested (through a call to
111 @code{bfd_canonicalize_symtab}, a request gets through to
112 @code{get_normalized_symtab}. This reads the symbol table from the
113 coff file and swaps all the structures inside into the internal form.
114 It also fixes up all the pointers in the table (represented in the file
115 by offsets from the first symbol in the table) into physical pointers
116 to elements in the new internal table. This involves some work since
117 the meanings of fields changes depending upon context; a field that is a
118 pointer to another structure in the symbol table at one moment may be
119 the size in bytes of a structure in the next.
120
121 Another pass is made over the table. All symbols which mark file names
122 (@code{C_FILE} symbols) are modified so that the internal string
123 points to the value in the auxent (the real filename) rather than the
124 normal text associated with the symbol (@code{".file"}).
125
126 At this time the symbol names are moved around. Coff stores all
127 symbols less than nine characters long physically within the symbol
128 table, longer strings are kept at the end of the file in the string
129 table. This pass moves all strings into memory, and replaces them with
130 pointers to the strings.
131
132 The symbol table is massaged once again, this time to create the
133 canonical table used by the BFD application. Each symbol is inspected
134 in turn, and a decision made (using the @code{sclass} field) about the
135 various flags to set in the @code{asymbol} @xref{Symbols}. The
136 generated canonical table shares strings with the hidden internal
137 symbol table.
138
139 Any linenumbers are read from the coff file too, and attached to the
140 symbols which own the functions the linenumbers belong to.
141
142 @subsubsection Symbol Writing
143 Writing a symbol to a coff file which didn't come from a coff file
144 will lose any debugging information. The @code{asymbol} structure
145 remembers the BFD from which was born, and on output the back end
146 makes sure that the same destination target as source target is
147 present.
148
149 When the symbols have come from a coff file then all the debugging
150 information is preserved.
151
152 Symbol tables are provided for writing to the back end in a vector of
153 pointers to pointers. This allows applications like the linker to
154 accumulate and output large symbol tables without having to do too
155 much byte copying.
156
157 The symbol table is not output to a writable BFD until it is closed.
158 The order of operations on the canonical symbol table at that point
159 are:
160 @table @code
161 @item coff_renumber_symbols
162 This function runs through the provided symbol table and patches each
163 symbol marked as a file place holder (@code{C_FILE}) to point to the
164 next file place holder in the list. It also marks each @code{offset}
165 field in the list with the offset from the first symbol of the current
166 symbol.
167
168 Another function of this procedure is to turn the canonical value form
169 of BFD into the form used by coff. Internally, BFD expects symbol
170 values to be offsets from a section base; so a symbol physically at
171 0x120, but in a section starting at 0x100, would have the value 0x20.
172 Coff expects symbols to contain their final value, so symbols have
173 their values changed at this point to reflect their sum with their
174 owning section. Note that this transformation uses the
175 @code{output_section} field of the @code{asymbol}'s @code{asection}
176 @xref{Sections}.
177 @item coff_mangle_symbols
178 This routine runs though the provided symbol table and uses the
179 offsets generated by the previous pass and the pointers generated when
180 the symbol table was read in to create the structured hierachy
181 required by coff. It changes each pointer to a symbol to an index into
182 the symbol table of the symbol being referenced.
183 @item coff_write_symbols
184 This routine runs through the symbol table and patches up the symbols
185 from their internal form into the coff way, calls the bit twiddlers
186 and writes out the tabel to the file.
187 @end table
188 */
189
190 /*proto*
191
192 The hidden information for an asymbol is:
193
194 *+++
195
196 $ typedef struct coff_ptr_struct
197 $ {
198
199 Remembers the offset from the first symbol in the file for this
200 symbol. Generated by @code{coff_renumber_symbols}.
201
202 $   unsigned int offset;
203
204 Should the tag field of this symbol be renumbered.
205 Created by @code{coff_pointerize_aux}.
206
207 $   char fix_tag;
208
209 Should the endidx field of this symbol be renumbered.
210 Created by @code{coff_pointerize_aux}.
211
212 $   char fix_end;
213
214 The container for the symbol structure as read and translated from the file.
215
216 $   union {
217 $     union internal_auxent auxent;
218 $     struct internal_syment syment;
219 $   } u;
220 $ } combined_entry_type;
221 $
222
223 *---
224
225 Each canonical asymbol really looks like this:
226
227 *+++
228
229 $ typedef struct coff_symbol_struct
230 $ {
231
232 The actual symbol which the rest of BFD works with
233
234 $   asymbol symbol;
235
236 A pointer to the hidden information for this symbol
237
238 $   combined_entry_type *native;
239
240 A pointer to the linenumber information for this symbol
241
242 $   struct lineno_cache_entry *lineno;
243 $ } coff_symbol_type;
244
245 *---
246
247 */
248
249 /* $Id$ */
250 /* Most of this hacked by Steve Chamberlain, steve@cygnus.com */
251
252
253 #define PUTWORD bfd_h_put_32
254 #define PUTHALF bfd_h_put_16
255
256 #ifndef GET_FCN_LNNOPTR
257 #define GET_FCN_LNNOPTR(abfd, ext)  bfd_h_get_32(abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_fcn.x_lnnoptr)
258 #endif
259
260 #ifndef GET_FCN_ENDNDX
261 #define GET_FCN_ENDNDX(abfd, ext)  bfd_h_get_32(abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_fcn.x_endndx)
262 #endif
263
264 #ifndef PUT_FCN_LNNOPTR
265 #define PUT_FCN_LNNOPTR(abfd, in, ext)  PUTWORD(abfd,  in, (bfd_byte *) ext->x_sym.x_fcnary.x_fcn.x_lnnoptr)
266 #endif
267 #ifndef PUT_FCN_ENDNDX
268 #define PUT_FCN_ENDNDX(abfd, in, ext) PUTWORD(abfd, in, (bfd_byte *) ext->x_sym.x_fcnary.x_fcn.x_endndx)
269 #endif
270 #ifndef GET_LNSZ_LNNO
271 #define GET_LNSZ_LNNO(abfd, ext) bfd_h_get_16(abfd, (bfd_byte *) ext->x_sym.x_misc.x_lnsz.x_lnno)
272 #endif
273 #ifndef GET_LNSZ_SIZE
274 #define GET_LNSZ_SIZE(abfd, ext) bfd_h_get_16(abfd, (bfd_byte *) ext->x_sym.x_misc.x_lnsz.x_size)
275 #endif
276 #ifndef PUT_LNSZ_LNNO
277 #define PUT_LNSZ_LNNO(abfd, in, ext) bfd_h_put_16(abfd, in, (bfd_byte *)ext->x_sym.x_misc.x_lnsz.x_lnno)
278 #endif
279 #ifndef PUT_LNSZ_SIZE
280 #define PUT_LNSZ_SIZE(abfd, in, ext) bfd_h_put_16(abfd, in, (bfd_byte*) ext->x_sym.x_misc.x_lnsz.x_size)
281 #endif
282 #ifndef GET_SCN_SCNLEN
283 #define GET_SCN_SCNLEN(abfd,  ext) bfd_h_get_32(abfd, (bfd_byte *) ext->x_scn.x_scnlen)
284 #endif
285 #ifndef GET_SCN_NRELOC
286 #define GET_SCN_NRELOC(abfd,  ext) bfd_h_get_16(abfd, (bfd_byte *)ext->x_scn.x_nreloc)
287 #endif
288 #ifndef GET_SCN_NLINNO
289 #define GET_SCN_NLINNO(abfd, ext)  bfd_h_get_16(abfd, (bfd_byte *)ext->x_scn.x_nlinno)
290 #endif
291 #ifndef PUT_SCN_SCNLEN
292 #define PUT_SCN_SCNLEN(abfd,in, ext) bfd_h_put_32(abfd, in, (bfd_byte *) ext->x_scn.x_scnlen)
293 #endif
294 #ifndef PUT_SCN_NRELOC
295 #define PUT_SCN_NRELOC(abfd,in, ext) bfd_h_put_16(abfd, in, (bfd_byte *)ext->x_scn.x_nreloc)
296 #endif
297 #ifndef PUT_SCN_NLINNO
298 #define PUT_SCN_NLINNO(abfd,in, ext)  bfd_h_put_16(abfd,in, (bfd_byte *) ext->x_scn.x_nlinno)
299 #endif
300
301
302 \f
303 /* void warning(); */
304
305 /*
306  * Return a word with STYP_* (scnhdr.s_flags) flags set to represent the
307  * incoming SEC_* flags.  The inverse of this function is styp_to_sec_flags().
308  * NOTE: If you add to/change this routine, you should mirror the changes
309  *      in styp_to_sec_flags().
310  */
311 static long
312 DEFUN(sec_to_styp_flags, (sec_name, sec_flags),
313         CONST char *            sec_name        AND
314         flagword        sec_flags)
315 {
316     long styp_flags = 0;
317
318     if (!strcmp(sec_name, _TEXT)) {
319         return((long)STYP_TEXT);
320     } else if (!strcmp(sec_name, _DATA)) {
321         return((long)STYP_DATA);
322     } else if (!strcmp(sec_name, _BSS)) {
323         return((long)STYP_BSS);
324     }
325
326 /* Try and figure out what it should be */
327    if (sec_flags & SEC_CODE) styp_flags = STYP_TEXT;
328    if (sec_flags & SEC_DATA) styp_flags = STYP_DATA;
329    else if (sec_flags & SEC_READONLY)
330 #ifdef STYP_LIT /* 29k readonly text/data section */
331         styp_flags = STYP_LIT;
332 #else
333         styp_flags = STYP_TEXT;
334 #endif  /* STYP_LIT */
335    else if (sec_flags & SEC_LOAD) styp_flags = STYP_TEXT;
336
337    if (styp_flags == 0) styp_flags = STYP_BSS;
338
339    return(styp_flags);
340 }
341 /*
342  * Return a word with SEC_* flags set to represent the incoming
343  * STYP_* flags (from scnhdr.s_flags).   The inverse of this
344  * function is sec_to_styp_flags().
345  * NOTE: If you add to/change this routine, you should mirror the changes
346  *      in sec_to_styp_flags().
347  */
348 static flagword
349 DEFUN(styp_to_sec_flags, (styp_flags),
350         long    styp_flags)
351 {
352     flagword    sec_flags=0;
353
354     if ((styp_flags & STYP_TEXT) || (styp_flags & STYP_DATA))
355         sec_flags = (SEC_LOAD | SEC_ALLOC);
356     else if (styp_flags & STYP_BSS)
357         sec_flags = SEC_ALLOC;
358
359 #ifdef STYP_LIT         /* A29k readonly text/data section type */
360     if ((styp_flags & STYP_LIT) == STYP_LIT)
361         sec_flags = (SEC_LOAD | SEC_ALLOC | SEC_READONLY);
362 #endif  /* STYP_LIT */
363
364     return(sec_flags);
365 }
366
367 #define get_index(symbol)       ((int) (symbol)->value)
368 #define set_index(symbol, idx)  ((symbol)->value = (idx))
369
370 /*  **********************************************************************
371 Here are all the routines for swapping the structures seen in the
372 outside world into the internal forms.
373 */
374
375
376 static void
377 DEFUN(bfd_swap_reloc_in,(abfd, reloc_src, reloc_dst),
378       bfd            *abfd AND
379       RELOC *reloc_src AND
380       struct internal_reloc *reloc_dst)
381 {
382   reloc_dst->r_vaddr = bfd_h_get_32(abfd, (bfd_byte *)reloc_src->r_vaddr);
383   reloc_dst->r_symndx = bfd_h_get_32(abfd, (bfd_byte *) reloc_src->r_symndx);
384
385 #ifdef RS6000COFF_C
386   reloc_dst->r_type = bfd_h_get_8(abfd, reloc_src->r_type);
387   reloc_dst->r_size = bfd_h_get_8(abfd, reloc_src->r_size);
388 #else
389   reloc_dst->r_type = bfd_h_get_16(abfd, (bfd_byte *) reloc_src->r_type);
390 #endif
391
392 #if M88
393   reloc_dst->r_offset = bfd_h_get_16(abfd, (bfd_byte *) reloc_src->r_offset);
394 #endif
395 }
396
397
398 static unsigned int
399 DEFUN(coff_swap_reloc_out,(abfd, src, dst),
400       bfd       *abfd AND
401       PTR       src AND
402       PTR       dst)
403 {
404   struct internal_reloc *reloc_src = (struct internal_reloc *)src;
405   struct external_reloc *reloc_dst = (struct external_reloc *)dst;
406   bfd_h_put_32(abfd, reloc_src->r_vaddr, (bfd_byte *) reloc_dst->r_vaddr);
407   bfd_h_put_32(abfd, reloc_src->r_symndx, (bfd_byte *) reloc_dst->r_symndx);
408   bfd_h_put_16(abfd, reloc_src->r_type, (bfd_byte *) reloc_dst->r_type);
409 #if M88
410   bfd_h_put_16(abfd, reloc_src->r_offset, (bfd_byte *) reloc_dst->r_offset);
411 #endif
412   return sizeof(struct external_reloc);
413 }
414
415 static void
416 DEFUN(bfd_swap_filehdr_in,(abfd, filehdr_src, filehdr_dst),
417       bfd            *abfd AND
418       FILHDR         *filehdr_src AND
419       struct internal_filehdr *filehdr_dst)
420 {
421   filehdr_dst->f_magic = bfd_h_get_16(abfd, (bfd_byte *) filehdr_src->f_magic);
422   filehdr_dst->f_nscns = bfd_h_get_16(abfd, (bfd_byte *)filehdr_src-> f_nscns);
423   filehdr_dst->f_timdat = bfd_h_get_32(abfd, (bfd_byte *)filehdr_src-> f_timdat);
424   filehdr_dst->f_symptr = bfd_h_get_32(abfd, (bfd_byte *)filehdr_src-> f_symptr);
425   filehdr_dst->f_nsyms = bfd_h_get_32(abfd, (bfd_byte *)filehdr_src-> f_nsyms);
426   filehdr_dst->f_opthdr = bfd_h_get_16(abfd, (bfd_byte *)filehdr_src-> f_opthdr);
427   filehdr_dst->f_flags = bfd_h_get_16(abfd, (bfd_byte *)filehdr_src-> f_flags);
428 }
429
430 static  unsigned int
431 DEFUN(coff_swap_filehdr_out,(abfd, in, out),
432       bfd       *abfd AND
433       PTR       in AND
434       PTR       out)
435 {
436   struct internal_filehdr *filehdr_in = (struct internal_filehdr *)in;
437   FILHDR *filehdr_out = (FILHDR *)out;
438   bfd_h_put_16(abfd, filehdr_in->f_magic, (bfd_byte *) filehdr_out->f_magic);
439   bfd_h_put_16(abfd, filehdr_in->f_nscns, (bfd_byte *) filehdr_out->f_nscns);
440   bfd_h_put_32(abfd, filehdr_in->f_timdat, (bfd_byte *) filehdr_out->f_timdat);
441   bfd_h_put_32(abfd, filehdr_in->f_symptr, (bfd_byte *) filehdr_out->f_symptr);
442   bfd_h_put_32(abfd, filehdr_in->f_nsyms, (bfd_byte *) filehdr_out->f_nsyms);
443   bfd_h_put_16(abfd, filehdr_in->f_opthdr, (bfd_byte *) filehdr_out->f_opthdr);
444   bfd_h_put_16(abfd, filehdr_in->f_flags, (bfd_byte *) filehdr_out->f_flags);
445   return sizeof(FILHDR);
446 }
447
448
449 #ifndef NO_COFF_SYMBOLS
450
451 static void
452 DEFUN(coff_swap_sym_in,(abfd, ext1, in1),
453       bfd            *abfd AND
454       PTR ext1 AND
455       PTR in1)
456 {
457   SYMENT *ext = (SYMENT *)ext1;
458   struct internal_syment      *in = (struct internal_syment *)in1;
459
460   if( ext->e.e_name[0] == 0) {
461     in->_n._n_n._n_zeroes = 0;
462     in->_n._n_n._n_offset = bfd_h_get_32(abfd, (bfd_byte *) ext->e.e.e_offset);
463   }
464   else {
465 #if SYMNMLEN != E_SYMNMLEN
466    -> Error, we need to cope with truncating or extending SYMNMLEN!;
467 #else
468     memcpy(in->_n._n_name, ext->e.e_name, SYMNMLEN);
469 #endif
470   }
471   in->n_value = bfd_h_get_32(abfd, (bfd_byte *) ext->e_value);
472   in->n_scnum = bfd_h_get_16(abfd, (bfd_byte *) ext->e_scnum);
473   if (sizeof(ext->e_type) == 2){
474     in->n_type = bfd_h_get_16(abfd, (bfd_byte *) ext->e_type);
475   }
476   else {
477     in->n_type = bfd_h_get_32(abfd, (bfd_byte *) ext->e_type);
478   }
479   in->n_sclass = bfd_h_get_8(abfd, ext->e_sclass);
480   in->n_numaux = bfd_h_get_8(abfd, ext->e_numaux);
481 }
482
483 static unsigned int
484 DEFUN(coff_swap_sym_out,(abfd, inp, extp),
485       bfd       *abfd AND
486       PTR       inp AND
487       PTR       extp)
488 {
489   struct internal_syment *in = (struct internal_syment *)inp;
490   SYMENT *ext =(SYMENT *)extp;
491   if(in->_n._n_name[0] == 0) {
492     bfd_h_put_32(abfd, 0, (bfd_byte *) ext->e.e.e_zeroes);
493     bfd_h_put_32(abfd, in->_n._n_n._n_offset, (bfd_byte *)  ext->e.e.e_offset);
494   }
495   else {
496 #if SYMNMLEN != E_SYMNMLEN
497     -> Error, we need to cope with truncating or extending SYMNMLEN!;
498 #else
499     memcpy(ext->e.e_name, in->_n._n_name, SYMNMLEN);
500 #endif
501   }
502   bfd_h_put_32(abfd,  in->n_value , (bfd_byte *) ext->e_value);
503   bfd_h_put_16(abfd,  in->n_scnum , (bfd_byte *) ext->e_scnum);
504   if (sizeof(ext->e_type) == 2)
505       {
506         bfd_h_put_16(abfd,  in->n_type , (bfd_byte *) ext->e_type);
507       }
508   else
509       {
510         bfd_h_put_32(abfd,  in->n_type , (bfd_byte *) ext->e_type);
511       }
512   bfd_h_put_8(abfd,  in->n_sclass , ext->e_sclass);
513   bfd_h_put_8(abfd,  in->n_numaux , ext->e_numaux);
514   return sizeof(SYMENT);
515 }
516
517 static void
518 DEFUN(coff_swap_aux_in,(abfd, ext1, type, class, in1),
519       bfd            *abfd AND
520       PTR             ext1 AND
521       int             type AND
522       int             class AND
523       PTR             in1)
524 {
525   AUXENT    *ext = (AUXENT *)ext1;
526   union internal_auxent  *in = (union internal_auxent *)in1;
527   switch (class) {
528   case C_FILE:
529     if (ext->x_file.x_fname[0] == 0) {
530       in->x_file.x_n.x_zeroes = 0;
531       in->x_file.x_n.x_offset  = bfd_h_get_32(abfd, (bfd_byte *) ext->x_file.x_n.x_offset);
532     } else {
533 #if FILNMLEN != E_FILNMLEN
534    -> Error, we need to cope with truncating or extending FILNMLEN!;
535 #else
536       memcpy (in->x_file.x_fname, ext->x_file.x_fname, FILNMLEN);
537 #endif
538     }
539
540     break;
541   case C_STAT:
542 #ifdef C_LEAFSTAT
543   case C_LEAFSTAT:
544 #endif
545   case C_HIDDEN:
546     if (type == T_NULL) {
547       in->x_scn.x_scnlen = GET_SCN_SCNLEN(abfd, ext);
548       in->x_scn.x_nreloc = GET_SCN_NRELOC(abfd, ext);
549       in->x_scn.x_nlinno = GET_SCN_NLINNO(abfd, ext);
550       break;
551     }
552   default:
553     in->x_sym.x_tagndx.l = bfd_h_get_32(abfd, (bfd_byte *) ext->x_sym.x_tagndx);
554 #ifndef NO_TVNDX
555     in->x_sym.x_tvndx = bfd_h_get_16(abfd, (bfd_byte *) ext->x_sym.x_tvndx);
556 #endif
557
558     if (ISARY(type) || class == C_BLOCK) {
559 #if DIMNUM != E_DIMNUM
560    -> Error, we need to cope with truncating or extending DIMNUM!;
561 #else
562       in->x_sym.x_fcnary.x_ary.x_dimen[0] = bfd_h_get_16(abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[0]);
563       in->x_sym.x_fcnary.x_ary.x_dimen[1] = bfd_h_get_16(abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[1]);
564       in->x_sym.x_fcnary.x_ary.x_dimen[2] = bfd_h_get_16(abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[2]);
565       in->x_sym.x_fcnary.x_ary.x_dimen[3] = bfd_h_get_16(abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[3]);
566 #endif
567     }
568       in->x_sym.x_fcnary.x_fcn.x_lnnoptr = GET_FCN_LNNOPTR(abfd, ext);
569       in->x_sym.x_fcnary.x_fcn.x_endndx.l = GET_FCN_ENDNDX(abfd, ext);
570
571     if (ISFCN(type)) {
572       in->x_sym.x_misc.x_fsize = bfd_h_get_32(abfd, (bfd_byte *) ext->x_sym.x_misc.x_fsize);
573     }
574     else {
575       in->x_sym.x_misc.x_lnsz.x_lnno = GET_LNSZ_LNNO(abfd, ext);
576       in->x_sym.x_misc.x_lnsz.x_size = GET_LNSZ_SIZE(abfd, ext);
577     }
578   }
579 }
580
581 static unsigned int
582 DEFUN(coff_swap_aux_out,(abfd, inp, type, class, extp),
583   bfd   *abfd AND
584   PTR   inp AND
585   int   type AND
586   int   class AND
587   PTR   extp)
588 {
589   union internal_auxent *in = (union internal_auxent *)inp;
590   AUXENT *ext = (AUXENT *)extp;
591   switch (class) {
592   case C_FILE:
593     if (in->x_file.x_fname[0] == 0) {
594       PUTWORD(abfd, 0, (bfd_byte *) ext->x_file.x_n.x_zeroes);
595       PUTWORD(abfd,
596               in->x_file.x_n.x_offset,
597               (bfd_byte *) ext->x_file.x_n.x_offset);
598     }
599     else {
600 #if FILNMLEN != E_FILNMLEN
601       -> Error, we need to cope with truncating or extending FILNMLEN!;
602 #else
603       memcpy (ext->x_file.x_fname, in->x_file.x_fname, FILNMLEN);
604 #endif
605     }
606     break;
607   case C_STAT:
608 #ifdef C_LEAFSTAT
609   case C_LEAFSTAT:
610 #endif
611   case C_HIDDEN:
612     if (type == T_NULL) {
613
614       PUT_SCN_SCNLEN(abfd, in->x_scn.x_scnlen, ext);
615       PUT_SCN_NRELOC(abfd, in->x_scn.x_nreloc, ext);
616       PUT_SCN_NLINNO(abfd, in->x_scn.x_nlinno, ext);
617       break;
618     }
619   default:
620     PUTWORD(abfd, in->x_sym.x_tagndx.l, (bfd_byte *) ext->x_sym.x_tagndx);
621 #ifndef NO_TVNDX
622     PUTWORD(abfd, in->x_sym.x_tvndx , (bfd_byte *) ext->x_sym.x_tvndx);
623 #endif
624
625     if (ISFCN(type)) {
626       PUTWORD(abfd, in->x_sym.x_misc.x_fsize, (bfd_byte *)  ext->x_sym.x_misc.x_fsize);
627       PUT_FCN_LNNOPTR(abfd,  in->x_sym.x_fcnary.x_fcn.x_lnnoptr, ext);
628       PUT_FCN_ENDNDX(abfd,  in->x_sym.x_fcnary.x_fcn.x_endndx.l, ext);
629     }
630     else {
631
632       if (ISARY(type) || class == C_BLOCK) {
633 #if DIMNUM != E_DIMNUM
634         -> Error, we need to cope with truncating or extending DIMNUM!;
635 #else
636         bfd_h_put_16(abfd, in->x_sym.x_fcnary.x_ary.x_dimen[0], (bfd_byte *)ext->x_sym.x_fcnary.x_ary.x_dimen[0]);
637         bfd_h_put_16(abfd, in->x_sym.x_fcnary.x_ary.x_dimen[1], (bfd_byte *)ext->x_sym.x_fcnary.x_ary.x_dimen[1]);
638         bfd_h_put_16(abfd, in->x_sym.x_fcnary.x_ary.x_dimen[2], (bfd_byte *)ext->x_sym.x_fcnary.x_ary.x_dimen[2]);
639         bfd_h_put_16(abfd, in->x_sym.x_fcnary.x_ary.x_dimen[3], (bfd_byte *)ext->x_sym.x_fcnary.x_ary.x_dimen[3]);
640 #endif
641       }
642       PUT_LNSZ_LNNO(abfd, in->x_sym.x_misc.x_lnsz.x_lnno, ext);
643       PUT_LNSZ_SIZE(abfd, in->x_sym.x_misc.x_lnsz.x_size, ext);
644
645       PUT_FCN_LNNOPTR(abfd,  in->x_sym.x_fcnary.x_fcn.x_lnnoptr, ext);
646       PUT_FCN_ENDNDX(abfd,  in->x_sym.x_fcnary.x_fcn.x_endndx.l, ext);
647
648
649     }
650   }
651 return sizeof(AUXENT);
652 }
653
654 #endif /* NO_COFF_SYMBOLS */
655
656 #ifndef NO_COFF_LINENOS
657
658 static void
659 DEFUN(coff_swap_lineno_in,(abfd, ext1, in1),
660       bfd            *abfd AND
661       PTR ext1 AND
662       PTR in1)
663 {
664   LINENO *ext = (LINENO *)ext1;
665   struct internal_lineno      *in = (struct internal_lineno *)in1;
666
667   in->l_addr.l_symndx = bfd_h_get_32(abfd, (bfd_byte *) ext->l_addr.l_symndx);
668 #if defined(M88)
669   in->l_lnno = bfd_h_get_32(abfd, (bfd_byte *) ext->l_lnno);
670 #else
671   in->l_lnno = bfd_h_get_16(abfd, (bfd_byte *) ext->l_lnno);
672 #endif
673 }
674
675 static unsigned int
676 DEFUN(coff_swap_lineno_out,(abfd, inp, outp),
677       bfd       *abfd AND
678       PTR       inp AND
679       PTR       outp)
680 {
681   struct internal_lineno *in = (struct internal_lineno *)inp;
682   struct external_lineno *ext = (struct external_lineno *)outp;
683   PUTWORD(abfd, in->l_addr.l_symndx, (bfd_byte *) ext->l_addr.l_symndx);
684 #if defined(M88)
685   PUTWORD(abfd, in->l_lnno, (bfd_byte *) ext->l_lnno);
686 #else
687   PUTHALF(abfd, in->l_lnno, (bfd_byte *) ext->l_lnno);
688 #endif
689   return sizeof(struct external_lineno);
690 }
691
692 #endif /* NO_COFF_LINENOS */
693
694
695 static void
696 DEFUN(bfd_swap_aouthdr_in,(abfd, aouthdr_ext1, aouthdr_int1),
697       bfd            *abfd AND
698       PTR aouthdr_ext1 AND
699       PTR aouthdr_int1)
700 {
701   AOUTHDR        *aouthdr_ext = (AOUTHDR *) aouthdr_ext1;
702   struct internal_aouthdr *aouthdr_int = (struct internal_aouthdr *)aouthdr_int1;
703
704   aouthdr_int->magic = bfd_h_get_16(abfd, (bfd_byte *) aouthdr_ext->magic);
705   aouthdr_int->vstamp = bfd_h_get_16(abfd, (bfd_byte *) aouthdr_ext->vstamp);
706   aouthdr_int->tsize = bfd_h_get_32(abfd, (bfd_byte *) aouthdr_ext->tsize);
707   aouthdr_int->dsize = bfd_h_get_32(abfd, (bfd_byte *) aouthdr_ext->dsize);
708   aouthdr_int->bsize = bfd_h_get_32(abfd, (bfd_byte *) aouthdr_ext->bsize);
709   aouthdr_int->entry = bfd_h_get_32(abfd, (bfd_byte *) aouthdr_ext->entry);
710   aouthdr_int->text_start = bfd_h_get_32(abfd, (bfd_byte *) aouthdr_ext->text_start);
711   aouthdr_int->data_start = bfd_h_get_32(abfd, (bfd_byte *) aouthdr_ext->data_start);
712 #ifdef I960
713   aouthdr_int->tagentries = bfd_h_get_32(abfd, (bfd_byte *) aouthdr_ext->tagentries);
714 #endif
715
716 #ifdef RS6000COFF_C
717   aouthdr_int->o_toc = bfd_h_get_32(abfd, aouthdr_ext->o_toc);
718   aouthdr_int->o_snentry = bfd_h_get_16(abfd, aouthdr_ext->o_snentry);
719   aouthdr_int->o_sntext = bfd_h_get_16(abfd, aouthdr_ext->o_sntext);
720   aouthdr_int->o_sndata = bfd_h_get_16(abfd, aouthdr_ext->o_sndata);
721   aouthdr_int->o_sntoc = bfd_h_get_16(abfd, aouthdr_ext->o_sntoc);
722   aouthdr_int->o_snloader = bfd_h_get_16(abfd, aouthdr_ext->o_snloader);
723   aouthdr_int->o_snbss = bfd_h_get_16(abfd, aouthdr_ext->o_snbss);
724   aouthdr_int->o_algntext = bfd_h_get_16(abfd, aouthdr_ext->o_algntext);
725   aouthdr_int->o_algndata = bfd_h_get_16(abfd, aouthdr_ext->o_algndata);
726   aouthdr_int->o_modtype = bfd_h_get_16(abfd, aouthdr_ext->o_modtype);
727   aouthdr_int->o_maxstack = bfd_h_get_32(abfd, aouthdr_ext->o_maxstack);
728 #endif
729 }
730
731 static unsigned int
732 DEFUN(coff_swap_aouthdr_out,(abfd, in, out),
733       bfd       *abfd AND
734       PTR       in AND
735       PTR       out)
736 {
737   struct internal_aouthdr *aouthdr_in = (struct internal_aouthdr *)in;
738   AOUTHDR *aouthdr_out = (AOUTHDR *)out;
739   bfd_h_put_16(abfd, aouthdr_in->magic, (bfd_byte *) aouthdr_out->magic);
740   bfd_h_put_16(abfd, aouthdr_in->vstamp, (bfd_byte *) aouthdr_out->vstamp);
741   bfd_h_put_32(abfd, aouthdr_in->tsize, (bfd_byte *) aouthdr_out->tsize);
742   bfd_h_put_32(abfd, aouthdr_in->dsize, (bfd_byte *) aouthdr_out->dsize);
743   bfd_h_put_32(abfd, aouthdr_in->bsize, (bfd_byte *) aouthdr_out->bsize);
744   bfd_h_put_32(abfd, aouthdr_in->entry, (bfd_byte *) aouthdr_out->entry);
745   bfd_h_put_32(abfd, aouthdr_in->text_start,
746                (bfd_byte *) aouthdr_out->text_start);
747   bfd_h_put_32(abfd, aouthdr_in->data_start, (bfd_byte *) aouthdr_out->data_start);
748 #ifdef I960
749   bfd_h_put_32(abfd, aouthdr_in->tagentries, (bfd_byte *) aouthdr_out->tagentries);
750 #endif
751   return sizeof(AOUTHDR);
752 }
753
754 static void
755 DEFUN(coff_swap_scnhdr_in,(abfd, scnhdr_ext, scnhdr_int),
756       bfd            *abfd AND
757       SCNHDR         *scnhdr_ext AND
758       struct internal_scnhdr *scnhdr_int)
759 {
760   memcpy(scnhdr_int->s_name, scnhdr_ext->s_name, sizeof(scnhdr_int->s_name));
761   scnhdr_int->s_vaddr = bfd_h_get_32(abfd, (bfd_byte *) scnhdr_ext->s_vaddr);
762   scnhdr_int->s_paddr = bfd_h_get_32(abfd, (bfd_byte *) scnhdr_ext->s_paddr);
763   scnhdr_int->s_size = bfd_h_get_32(abfd, (bfd_byte *) scnhdr_ext->s_size);
764   scnhdr_int->s_scnptr = bfd_h_get_32(abfd, (bfd_byte *) scnhdr_ext->s_scnptr);
765   scnhdr_int->s_relptr = bfd_h_get_32(abfd, (bfd_byte *) scnhdr_ext->s_relptr);
766   scnhdr_int->s_lnnoptr = bfd_h_get_32(abfd, (bfd_byte *) scnhdr_ext->s_lnnoptr);
767   scnhdr_int->s_flags = bfd_h_get_32(abfd, (bfd_byte *) scnhdr_ext->s_flags);
768 #if defined(M88)
769   scnhdr_int->s_nreloc = bfd_h_get_32(abfd, (bfd_byte *) scnhdr_ext->s_nreloc);
770   scnhdr_int->s_nlnno = bfd_h_get_32(abfd, (bfd_byte *) scnhdr_ext->s_nlnno);
771 #else
772   scnhdr_int->s_nreloc = bfd_h_get_16(abfd, (bfd_byte *) scnhdr_ext->s_nreloc);
773   scnhdr_int->s_nlnno = bfd_h_get_16(abfd, (bfd_byte *) scnhdr_ext->s_nlnno);
774 #endif
775 #ifdef I960
776   scnhdr_int->s_align = bfd_h_get_32(abfd, (bfd_byte *) scnhdr_ext->s_align);
777 #endif
778 }
779
780 static unsigned int
781 DEFUN(coff_swap_scnhdr_out,(abfd, in, out),
782       bfd       *abfd AND
783       PTR       in AND
784       PTR       out)
785 {
786   struct internal_scnhdr *scnhdr_int = (struct internal_scnhdr *)in;
787   SCNHDR *scnhdr_ext = (SCNHDR *)out;
788   memcpy(scnhdr_ext->s_name, scnhdr_int->s_name, sizeof(scnhdr_int->s_name));
789   PUTWORD(abfd, scnhdr_int->s_vaddr, (bfd_byte *) scnhdr_ext->s_vaddr);
790   PUTWORD(abfd, scnhdr_int->s_paddr, (bfd_byte *) scnhdr_ext->s_paddr);
791   PUTWORD(abfd, scnhdr_int->s_size, (bfd_byte *) scnhdr_ext->s_size);
792   PUTWORD(abfd, scnhdr_int->s_scnptr, (bfd_byte *) scnhdr_ext->s_scnptr);
793   PUTWORD(abfd, scnhdr_int->s_relptr, (bfd_byte *) scnhdr_ext->s_relptr);
794   PUTWORD(abfd, scnhdr_int->s_lnnoptr, (bfd_byte *) scnhdr_ext->s_lnnoptr);
795   PUTWORD(abfd, scnhdr_int->s_flags, (bfd_byte *) scnhdr_ext->s_flags);
796 #if defined(M88)
797   PUTWORD(abfd, scnhdr_int->s_nlnno, (bfd_byte *) scnhdr_ext->s_nlnno);
798   PUTWORD(abfd, scnhdr_int->s_nreloc, (bfd_byte *) scnhdr_ext->s_nreloc);
799 #else
800   PUTHALF(abfd, scnhdr_int->s_nlnno, (bfd_byte *) scnhdr_ext->s_nlnno);
801   PUTHALF(abfd, scnhdr_int->s_nreloc, (bfd_byte *) scnhdr_ext->s_nreloc);
802 #endif
803
804 #if defined(I960)
805   PUTWORD(abfd, scnhdr_int->s_align, (bfd_byte *) scnhdr_ext->s_align);
806 #endif
807   return sizeof(SCNHDR);
808 }
809
810
811 /*
812    initialize a section structure with information peculiar to this
813    particular implementation of coff
814 */
815
816 static          boolean
817 DEFUN(coff_new_section_hook,(abfd_ignore, section_ignore),
818       bfd            *abfd_ignore AND
819       asection       *section_ignore)
820 {
821   section_ignore->alignment_power = abfd_ignore->xvec->align_power_min;
822   return true;
823 }
824
825 /* Take a section header read from a coff file (in HOST byte order),
826    and make a BFD "section" out of it.  */
827 static          boolean
828 DEFUN(make_a_section_from_file,(abfd, hdr),
829       bfd            *abfd AND
830       struct internal_scnhdr  *hdr)
831 {
832     asection       *return_section;
833
834     {
835         /* Assorted wastage to null-terminate the name, thanks AT&T! */
836         char *name = bfd_alloc(abfd, sizeof (hdr->s_name)+1);
837         if (name == NULL) {
838             bfd_error = no_memory;
839             return false;
840         }
841         strncpy(name, (char *) &hdr->s_name[0], sizeof (hdr->s_name));
842         name[sizeof (hdr->s_name)] = 0;
843
844         return_section = bfd_make_section(abfd, name);
845         if (return_section == NULL)
846             return false;
847     }
848
849     /* s_paddr is presumed to be = to s_vaddr */
850 #define assign(to, from) return_section->to = hdr->from
851     assign(vma, s_vaddr);
852     /* assign (vma, s_vaddr); */
853     assign(size, s_size);
854     assign(filepos, s_scnptr);
855     assign(rel_filepos, s_relptr);
856     assign(reloc_count, s_nreloc);
857 #ifdef I960
858     {
859         /* FIXME, use a temp var rather than alignment_power */
860         assign(alignment_power, s_align);
861         {
862             unsigned int    i;
863             for (i = 0; i < 32; i++) {
864                 if ((1 << i) >= (int) (return_section->alignment_power)) {
865                     return_section->alignment_power = i;
866                     break;
867                 }
868             }
869         }
870     }
871 #endif
872     assign(line_filepos, s_lnnoptr);
873     /*
874        return_section->linesize =   hdr->s_nlnno * sizeof (struct lineno);
875     */
876
877     return_section->lineno_count = hdr->s_nlnno;
878     return_section->userdata = NULL;
879     return_section->next = (asection *) NULL;
880     return_section->flags = styp_to_sec_flags(hdr->s_flags);
881
882
883     if (hdr->s_nreloc != 0)
884         return_section->flags |= SEC_RELOC;
885     /* FIXME: should this check 'hdr->s_size > 0' */
886     if (hdr->s_scnptr != 0)
887         return_section->flags |= SEC_HAS_CONTENTS;
888     return true;
889 }
890 static          boolean
891 DEFUN(coff_mkobject,(abfd),
892       bfd            *abfd)
893 {
894   set_tdata (abfd, bfd_zalloc (abfd,sizeof(coff_data_type)));
895   if (coff_data(abfd) == 0) {
896     bfd_error = no_memory;
897     return false;
898   }
899   coff_data(abfd)->relocbase = 0;
900   return true;
901 }
902
903 static
904 bfd_target     *
905 DEFUN(coff_real_object_p,(abfd, nscns, internal_f, internal_a),
906     bfd            *abfd AND
907     unsigned        nscns AND
908   struct internal_filehdr *internal_f AND
909   struct internal_aouthdr *internal_a)
910 {
911   coff_data_type *coff;
912   enum bfd_architecture arch;
913   long machine;
914   size_t          readsize;     /* length of file_info */
915   SCNHDR *external_sections;
916
917   /* Build a play area */
918   if (coff_mkobject(abfd) != true)
919     return 0;
920   coff = coff_data(abfd);
921
922
923   external_sections = (SCNHDR *)bfd_alloc(abfd, readsize = (nscns * SCNHSZ));
924
925   if (bfd_read((PTR)external_sections, 1, readsize, abfd) != readsize) {
926     goto fail;
927   }
928
929
930   /* Now copy data as required; construct all asections etc */
931   coff->symbol_index_slew = 0;
932   coff->relocbase =0;
933   coff->raw_syment_count = 0;
934   coff->raw_linenos = 0;
935   coff->raw_syments = 0;
936   coff->sym_filepos =0;
937   coff->flags = internal_f->f_flags;
938   if (nscns != 0) {
939     unsigned int    i;
940     for (i = 0; i < nscns; i++) {
941       struct internal_scnhdr tmp;
942       coff_swap_scnhdr_in(abfd, external_sections + i, &tmp);
943       make_a_section_from_file(abfd,&tmp);
944     }
945   }
946   /* Determine the machine architecture and type.  */
947 machine = 0;
948   switch (internal_f->f_magic) {
949 #ifdef I386MAGIC
950   case I386MAGIC:
951     arch = bfd_arch_i386;
952     machine = 0;
953     break;
954 #endif
955
956 #ifdef A29K_MAGIC_BIG
957   case  A29K_MAGIC_BIG:
958   case  A29K_MAGIC_LITTLE:
959     arch = bfd_arch_a29k;
960     machine = 0;
961     break;
962 #endif
963
964 #ifdef MIPS
965   case  MIPS_MAGIC_1:
966   case  MIPS_MAGIC_2:
967   case  MIPS_MAGIC_3:
968     arch = bfd_arch_mips;
969     machine = 0;
970     break;
971 #endif
972
973 #ifdef MC68MAGIC
974   case MC68MAGIC:
975   case M68MAGIC:
976     arch = bfd_arch_m68k;
977     machine = 68020;
978     break;
979 #endif
980 #ifdef MC88MAGIC
981   case MC88MAGIC:
982   case MC88DMAGIC:
983   case MC88OMAGIC:
984     arch = bfd_arch_m88k;
985     machine = 88100;
986     break;
987 #endif
988 #ifdef I960
989 #ifdef I960ROMAGIC
990   case I960ROMAGIC:
991   case I960RWMAGIC:
992     arch = bfd_arch_i960;
993     switch (F_I960TYPE & internal_f->f_flags)
994         {
995         default:
996         case F_I960CORE:
997           machine = bfd_mach_i960_core;
998           break;
999         case F_I960KB:
1000           machine = bfd_mach_i960_kb_sb;
1001           break;
1002         case  F_I960MC:
1003           machine = bfd_mach_i960_mc;
1004           break;
1005         case F_I960XA:
1006           machine = bfd_mach_i960_xa;
1007           break;
1008         case F_I960CA:
1009           machine = bfd_mach_i960_ca;
1010           break;
1011         case F_I960KA:
1012           machine = bfd_mach_i960_ka_sa;
1013           break;
1014         }
1015     break;
1016 #endif
1017 #endif
1018
1019 #ifdef U802ROMAGIC
1020   case U802ROMAGIC:
1021   case U802WRMAGIC:
1022   case U802TOCMAGIC:
1023     arch = bfd_arch_rs6000;
1024     machine = 6000;
1025     break;
1026 #endif
1027
1028
1029   default:                      /* Unreadable input file type */
1030  arch = bfd_arch_obscure;
1031     break;
1032   }
1033
1034   bfd_default_set_arch_mach(abfd, arch, machine);
1035   if (!(internal_f->f_flags & F_RELFLG))
1036     abfd->flags |= HAS_RELOC;
1037   if ((internal_f->f_flags & F_EXEC))
1038     abfd->flags |= EXEC_P;
1039   if (!(internal_f->f_flags & F_LNNO))
1040     abfd->flags |= HAS_LINENO;
1041   if (!(internal_f->f_flags & F_LSYMS))
1042     abfd->flags |= HAS_LOCALS;
1043
1044
1045   bfd_get_symcount(abfd) = internal_f->f_nsyms;
1046   if (internal_f->f_nsyms)
1047     abfd->flags |= HAS_SYMS;
1048
1049   coff->sym_filepos = internal_f->f_symptr;
1050
1051   /* These members communicate important constants about the symbol table
1052     to GDB's symbol-reading code.  These `constants' unfortunately vary
1053       from coff implementation to implementation...  */
1054 #ifndef NO_COFF_SYMBOLS
1055   coff->local_n_btmask = N_BTMASK;
1056   coff->local_n_btshft = N_BTSHFT;
1057   coff->local_n_tmask  = N_TMASK;
1058   coff->local_n_tshift = N_TSHIFT;
1059   coff->local_symesz   = SYMESZ;
1060   coff->local_auxesz   = AUXESZ;
1061   coff->local_linesz   = LINESZ;
1062 #endif
1063
1064   coff->symbols = (coff_symbol_type *) NULL;
1065   bfd_get_start_address(abfd) = internal_f->f_opthdr ? internal_a->entry : 0;
1066
1067   return abfd->xvec;
1068  fail:
1069   bfd_release(abfd, coff);
1070   return (bfd_target *)NULL;
1071 }
1072
1073 static bfd_target *
1074 DEFUN(coff_object_p,(abfd),
1075       bfd            *abfd)
1076 {
1077   int   nscns;
1078   FILHDR filehdr;
1079   AOUTHDR opthdr;
1080   struct internal_filehdr internal_f;
1081   struct internal_aouthdr internal_a;
1082
1083   bfd_error = system_call_error;
1084
1085   /* figure out how much to read */
1086   if (bfd_read((PTR) &filehdr, 1, FILHSZ, abfd) != FILHSZ)
1087     return 0;
1088
1089   bfd_swap_filehdr_in(abfd, &filehdr, &internal_f);
1090
1091   if (BADMAG(internal_f)) {
1092     bfd_error = wrong_format;
1093     return 0;
1094   }
1095   nscns =internal_f.f_nscns;
1096
1097   if (internal_f.f_opthdr) {
1098     if (bfd_read((PTR) &opthdr, 1,AOUTSZ, abfd) != AOUTSZ) {
1099       return 0;
1100     }
1101     bfd_swap_aouthdr_in(abfd, (char *)&opthdr, (char *)&internal_a);
1102   }
1103
1104   /* Seek past the opt hdr stuff */
1105   bfd_seek(abfd, internal_f.f_opthdr + FILHSZ, SEEK_SET);
1106
1107   /* if the optional header is NULL or not the correct size then
1108      quit; the only difference I can see between m88k dgux headers (MC88DMAGIC)
1109      and Intel 960 readwrite headers (I960WRMAGIC) is that the
1110      optional header is of a different size.
1111
1112      But the mips keeps extra stuff in it's opthdr, so dont check
1113      when doing that
1114      */
1115
1116 #if defined(M88) || defined(I960)
1117   if (internal_f.f_opthdr != 0 && AOUTSZ != internal_f.f_opthdr)
1118     return (bfd_target *)NULL;
1119 #endif
1120
1121   return coff_real_object_p(abfd, nscns, &internal_f, &internal_a);
1122 }
1123
1124
1125
1126 #ifndef NO_COFF_LINENOS
1127
1128 static void
1129 DEFUN(coff_count_linenumbers,(abfd),
1130       bfd            *abfd)
1131 {
1132   unsigned int    limit = bfd_get_symcount(abfd);
1133   unsigned int    i;
1134   asymbol       **p;
1135     {
1136       asection       *s = abfd->sections->output_section;
1137       while (s) {
1138         BFD_ASSERT(s->lineno_count == 0);
1139         s = s->next;
1140       }
1141     }
1142
1143
1144   for (p = abfd->outsymbols, i = 0; i < limit; i++, p++) {
1145     asymbol        *q_maybe = *p;
1146     if (q_maybe->the_bfd->xvec->flavour == bfd_target_coff_flavour) {
1147       coff_symbol_type *q = coffsymbol(q_maybe);
1148       if (q->lineno) {
1149         /*
1150           This symbol has a linenumber, increment the owning
1151           section's linenumber count
1152           */
1153         alent          *l = q->lineno;
1154         q->symbol.section->output_section->lineno_count++;
1155         l++;
1156         while (l->line_number) {
1157           q->symbol.section->output_section->lineno_count++;
1158           l++;
1159         }
1160       }
1161     }
1162   }
1163 }
1164
1165 #endif /* NO_COFF_LINENOS */
1166
1167 #ifndef NO_COFF_SYMBOLS
1168
1169 /*
1170   Takes a bfd and a symbol, returns a pointer to the coff specific area
1171   of the symbol if there is one.
1172   */
1173 static coff_symbol_type *
1174 DEFUN(coff_symbol_from,(ignore_abfd, symbol),
1175       bfd            *ignore_abfd AND
1176       asymbol        *symbol)
1177 {
1178   if (symbol->the_bfd->xvec->flavour != bfd_target_coff_flavour)
1179     return (coff_symbol_type *)NULL;
1180
1181   if (symbol->the_bfd->tdata == (PTR)NULL)
1182     return (coff_symbol_type *)NULL;
1183
1184   return  (coff_symbol_type *) symbol;
1185 }
1186
1187
1188
1189 static void
1190 DEFUN(fixup_symbol_value,(coff_symbol_ptr, syment),
1191 coff_symbol_type *coff_symbol_ptr AND
1192 struct internal_syment *syment)
1193 {
1194
1195   /* Normalize the symbol flags */
1196   if (coff_symbol_ptr->symbol.flags & BSF_FORT_COMM) {
1197     /* a common symbol is undefined with a value */
1198     syment->n_scnum = N_UNDEF;
1199     syment->n_value = coff_symbol_ptr->symbol.value;
1200   }
1201   else if (coff_symbol_ptr->symbol.flags & BSF_DEBUGGING) {
1202     syment->n_value = coff_symbol_ptr->symbol.value;
1203   }
1204   else if (coff_symbol_ptr->symbol.flags & BSF_UNDEFINED) {
1205     syment->n_scnum = N_UNDEF;
1206     syment->n_value = 0;
1207   }
1208   else if (coff_symbol_ptr->symbol.flags & BSF_ABSOLUTE) {
1209     syment->n_scnum = N_ABS;
1210     syment->n_value = coff_symbol_ptr->symbol.value;
1211   }
1212   else {
1213     if (coff_symbol_ptr->symbol.section) {
1214       syment->n_scnum    =
1215        coff_symbol_ptr->symbol.section->output_section->index+1;
1216
1217       syment->n_value =
1218        coff_symbol_ptr->symbol.value +
1219         coff_symbol_ptr->symbol.section->output_offset +
1220          coff_symbol_ptr->symbol.section->output_section->vma;
1221     }
1222     else {
1223       /* This can happen, but I don't know why yet (steve@cygnus.com) */
1224       syment->n_scnum = N_ABS;
1225       syment->n_value = coff_symbol_ptr->symbol.value;
1226     }
1227   }
1228 }
1229
1230 /* run through all the symbols in the symbol table and work out what
1231    their indexes into the symbol table will be when output
1232
1233  Coff requires that each C_FILE symbol points to the next one in the
1234  chain, and that the last one points to the first external symbol. We
1235  do that here too.
1236
1237 */
1238 static void
1239 DEFUN(coff_renumber_symbols,(bfd_ptr),
1240       bfd *bfd_ptr)
1241 {
1242   unsigned int symbol_count = bfd_get_symcount(bfd_ptr);
1243   asymbol **symbol_ptr_ptr = bfd_ptr->outsymbols;
1244   unsigned int native_index = 0;
1245   struct internal_syment *last_file = (struct internal_syment *)NULL;
1246   unsigned int symbol_index;
1247   for (symbol_index = 0; symbol_index < symbol_count; symbol_index++)
1248       {
1249         coff_symbol_type *coff_symbol_ptr = coff_symbol_from(bfd_ptr, symbol_ptr_ptr[symbol_index]);
1250         if (coff_symbol_ptr && coff_symbol_ptr->native) {
1251           combined_entry_type *s = coff_symbol_ptr->native;
1252           int i;
1253
1254           if (s->u.syment.n_sclass == C_FILE)
1255               {
1256                 if (last_file != (struct internal_syment *)NULL) {
1257                   last_file->n_value = native_index;
1258                 }
1259                 last_file = &(s->u.syment);
1260               }
1261           else {
1262
1263             /* Modify the symbol values according to their section and
1264                type */
1265
1266             fixup_symbol_value(coff_symbol_ptr, &(s->u.syment));
1267           }
1268           for (i = 0; i < s->u.syment.n_numaux + 1; i++) {
1269             s[i].offset = native_index ++;
1270           }
1271         }
1272         else {
1273           native_index++;
1274         }
1275       }
1276 }
1277
1278
1279 /*
1280  Run thorough the symbol table again, and fix it so that all pointers to
1281  entries are changed to the entries' index in the output symbol table.
1282
1283 */
1284 static void
1285 DEFUN(coff_mangle_symbols,(bfd_ptr),
1286       bfd *bfd_ptr)
1287 {
1288   unsigned int symbol_count = bfd_get_symcount(bfd_ptr);
1289   asymbol **symbol_ptr_ptr = bfd_ptr->outsymbols;
1290   unsigned int symbol_index;
1291
1292   for (symbol_index = 0; symbol_index < symbol_count; symbol_index++)
1293       {
1294         coff_symbol_type *coff_symbol_ptr =
1295           coff_symbol_from(bfd_ptr, symbol_ptr_ptr[symbol_index]);
1296
1297         if (coff_symbol_ptr && coff_symbol_ptr->native) {
1298           int i;
1299           combined_entry_type *s = coff_symbol_ptr->native;
1300
1301           for (i = 0; i < s->u.syment.n_numaux ; i++) {
1302             combined_entry_type *a = s + i + 1;
1303             if (a->fix_tag) {
1304               a->u.auxent.x_sym.x_tagndx.l =
1305                 a->u.auxent.x_sym.x_tagndx.p->offset;
1306             }
1307             if (a->fix_end) {
1308               a->u.auxent.x_sym.x_fcnary.x_fcn.x_endndx.l =
1309                 a->u.auxent.x_sym.x_fcnary.x_fcn.x_endndx.p->offset;
1310             }
1311
1312           }
1313         }
1314       }
1315 }
1316
1317 #if 0
1318     unsigned int symbol_count = bfd_get_symcount(bfd_ptr);
1319     asymbol **symbol_ptr_ptr = bfd_ptr->outsymbols;
1320     struct internal_syment *last_tagndx = (struct internal_syment *)NULL;
1321     struct internal_syment *last_file = (struct internal_syment *)NULL;
1322     struct internal_syment *last_fcn = (struct internal_syment *)NULL;
1323     struct internal_syment *block_stack[50];
1324     struct internal_syment **last_block = &block_stack[0];
1325     boolean first_time = true;
1326     unsigned int symbol_index;
1327     unsigned int native_index = 0;
1328
1329     for (symbol_index = 0; symbol_index < symbol_count; symbol_index++) {
1330       coff_symbol_type *coff_symbol_ptr =
1331         coff_symbol_from(bfd_ptr, symbol_ptr_ptr[symbol_index]);
1332       if (coff_symbol_ptr == (coff_symbol_type *)NULL) {
1333         /*
1334           This symbol has no coff information in it, it will take up
1335             only one slot in the output symbol table
1336               */
1337         native_index++;
1338       }
1339       else {
1340         struct internal_syment *syment = coff_symbol_ptr->native;
1341         if (syment == (struct internal_syment *)NULL) {
1342           native_index++;
1343         }
1344         else {
1345           /* Normalize the symbol flags */
1346           if (coff_symbol_ptr->symbol.flags & BSF_FORT_COMM) {
1347             /* a common symbol is undefined with a value */
1348             syment->n_scnum = N_UNDEF;
1349             syment->n_value = coff_symbol_ptr->symbol.value;
1350           }
1351           else if (coff_symbol_ptr->symbol.flags & BSF_DEBUGGING) {
1352             syment->n_value = coff_symbol_ptr->symbol.value;
1353           }
1354           else if (coff_symbol_ptr->symbol.flags & BSF_UNDEFINED) {
1355             syment->n_scnum = N_UNDEF;
1356             syment->n_value = 0;
1357           }
1358           else if (coff_symbol_ptr->symbol.flags & BSF_ABSOLUTE) {
1359             syment->n_scnum = N_ABS;
1360             syment->n_value = coff_symbol_ptr->symbol.value;
1361           }
1362           else {
1363             syment->n_scnum      =
1364               coff_symbol_ptr->symbol.section->output_section->index+1;
1365
1366             syment->n_value =
1367               coff_symbol_ptr->symbol.value +
1368                 coff_symbol_ptr->symbol.section->output_offset +
1369                   coff_symbol_ptr->symbol.section->output_section->vma;
1370           }
1371
1372           /* If this symbol ties up something then do it */
1373
1374           if (syment->n_sclass == C_FILE && last_file != (struct internal_syment *)NULL)
1375               {
1376                 last_file->n_value = native_index;
1377               }
1378           else if ((syment->n_sclass == C_EXT /* FIXME - may need C_HIDEXT */
1379                     || syment->n_sclass == C_STAT
1380 #ifdef C_LEAFEXT
1381                     || syment->n_sclass == C_LEAFEXT
1382                       || syment->n_sclass == C_LEAFSTAT
1383 #endif
1384                   )
1385                  && last_fcn != (struct internal_syment *)NULL)
1386             {
1387               union internal_auxent *auxent = (union internal_auxent *)(last_fcn+1);
1388               auxent->x_sym.x_fcnary.x_fcn.x_endndx.l = native_index;
1389               last_fcn = (struct internal_syment *)NULL;
1390             }
1391         else if (syment->n_sclass == C_EOS && last_tagndx != (struct internal_syment*)NULL)
1392             {
1393               union internal_auxent *auxent = (union internal_auxent *)(last_tagndx+1);
1394               /* Remember that we keep the native index in the offset
1395                  so patch the beginning of the struct to point to this
1396                  */
1397 /*if (last_
1398               auxent->x_sym.x_tagndx =    last_tagndx->_n._n_n._n_offset;*/
1399               auxent->x_sym.x_fcnary.x_fcn.x_endndx.l = syment->n_numaux + 1 + native_index;
1400               /* Now point the eos to the structure */
1401               auxent = (union internal_auxent *)(syment+1);
1402               auxent->x_sym.x_tagndx.l =  last_tagndx->_n._n_n._n_offset;
1403             }
1404         else if (syment->n_sclass == C_BLOCK
1405                  && coff_symbol_ptr->symbol.name[1] == 'e')
1406             {
1407               union internal_auxent *auxent = (union internal_auxent *)((*(--last_block))+1);
1408               auxent->x_sym.x_fcnary.x_fcn.x_endndx.l = native_index + syment->n_numaux + 1;
1409             }
1410         if (syment->n_sclass == C_EXT
1411             && !ISFCN(syment->n_type)
1412             && first_time == true
1413             && last_file != (struct internal_syment *)NULL) {
1414           /* This is the first external symbol seen which isn't a
1415              function place it in the last .file entry */
1416           last_file->n_value = native_index;
1417           first_time = false;
1418         }
1419 #ifdef C_LEAFPROC
1420         if (syment->n_sclass == C_LEAFPROC &&
1421             syment->n_numaux == 2) {
1422           union internal_auxent *auxent = (union internal_auxent *)(syment+2);
1423           /* This is the definition of a leaf proc, we'll relocate the
1424              address */
1425           auxent->x_bal.x_balntry = 
1426             coff_symbol_ptr->symbol.section->output_offset +
1427               coff_symbol_ptr->symbol.section->output_section->vma +
1428                 auxent->x_bal.x_balntry   ;
1429         }
1430 #endif
1431         /* If this symbol needs to be tied up then remember some facts */
1432         if (syment->n_sclass == C_FILE)
1433             {
1434               last_file = syment;
1435             }
1436         if (syment->n_numaux != 0) {
1437           /*
1438             If this symbol would like to point to something in the
1439             future then remember where it is
1440             */
1441           if (uses_x_sym_x_tagndx_p(bfd_ptr, syment)) {
1442             /*
1443               If this is a ref to a structure then we'll tie it up
1444               now - there are never any forward refs for one
1445               */
1446             if (syment->n_sclass == C_STRTAG ||
1447                 syment->n_sclass == C_ENTAG ||
1448                 syment->n_sclass == C_UNTAG) {
1449               last_tagndx = syment;
1450             }
1451             else {
1452               /*
1453                 This is a ref to a structure - the structure must
1454                 have been defined within the same file, and previous
1455                 to this point, so we can deduce the new tagndx
1456                 directly.
1457                 */
1458               union internal_auxent *auxent = (union internal_auxent *)(syment+1);
1459               bfd *bfd_ptr = coff_symbol_ptr->symbol.the_bfd;
1460               struct internal_syment *base = obj_raw_syments(bfd_ptr);
1461 /*            auxent->x_sym.x_tagndx = base[auxent->x_sym.x_tagndx]._n._n_n._n_offset;*/
1462             }
1463           }
1464           if (ISFCN(syment->n_type)) {
1465             last_fcn = syment;
1466           }
1467           if (syment->n_sclass == C_BLOCK
1468               && coff_symbol_ptr->symbol.name[1] == 'b')
1469               {
1470                 *last_block++ = syment;
1471               }
1472         }
1473         syment->_n._n_n._n_offset = native_index;
1474         native_index = native_index + 1 + syment->n_numaux;
1475       }
1476     }
1477   }
1478 }
1479
1480
1481 #endif
1482 static int string_size;
1483 static void
1484 DEFUN(coff_fix_symbol_name,(ignore_abfd, symbol, native),
1485   bfd *ignore_abfd AND
1486   asymbol *symbol AND
1487   combined_entry_type *native)
1488 {
1489   unsigned int    name_length;
1490   union internal_auxent *auxent;
1491   char *  name = ( char *)(symbol->name);
1492
1493   if (name == (char *) NULL) {
1494     /* coff symbols always have names, so we'll make one up */
1495     symbol->name = "strange";
1496     name = (char *)symbol->name;
1497   }
1498   name_length = strlen(name);
1499
1500   if (native->u.syment.n_sclass == C_FILE) {
1501     strncpy(native->u.syment._n._n_name, ".file", SYMNMLEN);
1502     auxent = &(native+1)->u.auxent;
1503
1504 #ifdef COFF_LONG_FILENAMES
1505     if (name_length <= FILNMLEN) {
1506       strncpy(auxent->x_file.x_fname, name, FILNMLEN);
1507     }
1508     else {
1509       auxent->x_file.x_n.x_offset = string_size + 4;
1510       auxent->x_file.x_n.x_zeroes = 0;
1511       string_size += name_length + 1;
1512     }
1513 #else
1514     strncpy(auxent->x_file.x_fname, name, FILNMLEN);
1515     if (name_length > FILNMLEN) {
1516       name[FILNMLEN] = '\0';
1517     }
1518 #endif
1519   }
1520   else
1521       {                         /* NOT A C_FILE SYMBOL */
1522         if (name_length <= SYMNMLEN) {
1523           /* This name will fit into the symbol neatly */
1524           strncpy(native->u.syment._n._n_name, symbol->name, SYMNMLEN);
1525         }
1526         else {
1527           native->u.syment._n._n_n._n_offset =  string_size + 4;
1528           native->u.syment._n._n_n._n_zeroes = 0;
1529           string_size += name_length + 1;
1530         }
1531       }
1532 }
1533
1534
1535
1536 static unsigned int
1537 DEFUN(coff_write_symbol,(abfd, symbol, native, written),
1538 bfd *abfd AND
1539 asymbol *symbol AND
1540 combined_entry_type *native AND
1541 unsigned int written)
1542 {
1543   unsigned int    numaux = native->u.syment.n_numaux;
1544   int             type = native->u.syment.n_type;
1545   int             class =  native->u.syment.n_sclass;
1546   SYMENT buf;
1547   unsigned int j;
1548
1549   coff_fix_symbol_name(abfd, symbol, native);
1550   coff_swap_sym_out(abfd, &native->u.syment, &buf);
1551   bfd_write((PTR)& buf, 1, SYMESZ, abfd);
1552   for (j = 0; j != native->u.syment.n_numaux;  j++)
1553       {
1554         AUXENT buf1;
1555         bzero((PTR)&buf, AUXESZ);
1556         coff_swap_aux_out(abfd,
1557                          &( (native + j + 1)->u.auxent), type, class, &buf1);
1558         bfd_write((PTR) (&buf1), 1, AUXESZ, abfd);
1559       }
1560   /*
1561     Reuse somewhere in the symbol to keep the index
1562     */
1563   set_index(symbol, written);
1564   return   written + 1 + numaux;
1565 }
1566
1567
1568 static unsigned int
1569 DEFUN(coff_write_alien_symbol,(abfd, symbol, written),
1570       bfd *abfd AND
1571       asymbol *symbol AND
1572       unsigned int written)
1573 {
1574   /*
1575     This symbol has been created by the loader, or come from a non
1576     coff format. It  has no native element to inherit, make our
1577     own
1578     */
1579  combined_entry_type *native;
1580  combined_entry_type dummy;
1581   native = &dummy;
1582   native->u.syment.n_type =  T_NULL;
1583 #ifdef I960
1584   native->u.syment.n_flags =  0;
1585 #endif
1586   if (symbol->flags & BSF_ABSOLUTE) {
1587     native->u.syment.n_scnum  =  N_ABS;
1588     native->u.syment.n_value =  symbol->value;
1589   }
1590   else if (symbol->flags & (BSF_UNDEFINED | BSF_FORT_COMM)) {
1591     native->u.syment.n_scnum =  N_UNDEF;
1592     native->u.syment.n_value =  symbol->value;
1593   }
1594   else if (symbol->flags & BSF_DEBUGGING) {
1595     /*
1596       remove name so it doesn't take up any space
1597       */
1598     symbol->name = "";
1599   }
1600   else {
1601     native->u.syment.n_scnum  =   symbol->section->output_section->index +
1602       1;
1603     native->u.syment.n_value =   symbol->value +
1604       symbol->section->output_section->vma +
1605         symbol->section->output_offset;
1606 #ifdef I960
1607     /* Copy the any flags from the the file hdr into the symbol  */
1608       {
1609         coff_symbol_type *c = coff_symbol_from(abfd, symbol);
1610         if (c != (coff_symbol_type *)NULL) {
1611           native->u.syment.n_flags =   c->symbol.the_bfd->flags;
1612         }
1613       }
1614 #endif
1615   }
1616
1617 #ifdef HASPAD1
1618   native->u.syment.pad1[0] = 0;
1619   native->u.syment.pad1[0] = 0;
1620 #endif
1621
1622   native->u.syment.n_type =  0;
1623   if (symbol->flags & BSF_LOCAL)
1624     native->u.syment.n_sclass =  C_STAT;
1625   else
1626     native->u.syment.n_sclass =  C_EXT;
1627   native->u.syment.n_numaux =  0;
1628
1629   return   coff_write_symbol(abfd, symbol, native, written);
1630 }
1631
1632 static unsigned int
1633 DEFUN(coff_write_native_symbol,(abfd, symbol,   written),
1634 bfd *abfd AND
1635 coff_symbol_type *symbol AND
1636 unsigned int written)
1637 {
1638   /*
1639     Does this symbol have an ascociated line number - if so then
1640     make it remember this symbol index. Also tag the auxent of
1641     this symbol to point to the right place in the lineno table
1642     */
1643   combined_entry_type *native = symbol->native;
1644
1645   alent          *lineno = symbol->lineno;
1646
1647   if (lineno) {
1648     unsigned int    count = 0;
1649     lineno[count].u.offset = written;
1650     if (native->u.syment.n_numaux) {
1651       union internal_auxent  *a = &((native+1)->u.auxent);
1652
1653       a->x_sym.x_fcnary.x_fcn.x_lnnoptr =
1654         symbol->symbol.section->output_section->moving_line_filepos;
1655     }
1656     /*
1657       And count and relocate all other linenumbers
1658       */
1659     count++;
1660     while (lineno[count].line_number) {
1661       lineno[count].u.offset +=
1662         symbol->symbol.section->output_section->vma +
1663           symbol->symbol.section->output_offset;
1664       count++;
1665     }
1666     symbol->symbol.section->output_section->moving_line_filepos +=
1667       count * LINESZ;
1668   }
1669   return coff_write_symbol(abfd, &( symbol->symbol), native,written);
1670 }
1671
1672 static void
1673 DEFUN(coff_write_symbols,(abfd),
1674       bfd            *abfd)
1675 {
1676   unsigned int    i;
1677   unsigned int    limit = bfd_get_symcount(abfd);
1678   unsigned int    written = 0;
1679
1680   asymbol       **p;
1681
1682   string_size = 0;
1683
1684
1685   /* Seek to the right place */
1686   bfd_seek(abfd, obj_sym_filepos(abfd), SEEK_SET);
1687
1688   /* Output all the symbols we have */
1689
1690   written = 0;
1691   for (p = abfd->outsymbols, i = 0; i < limit; i++, p++)
1692       {
1693         asymbol        *symbol = *p;
1694         coff_symbol_type *c_symbol = coff_symbol_from(abfd, symbol);
1695
1696         if (c_symbol == (coff_symbol_type *) NULL ||
1697             c_symbol->native == (combined_entry_type *)NULL)
1698             {
1699               written = coff_write_alien_symbol(abfd, symbol, written);
1700             }
1701         else
1702             {
1703               written = coff_write_native_symbol(abfd, c_symbol, written);
1704             }
1705
1706       }
1707
1708   bfd_get_symcount(abfd) = written;
1709
1710   /* Now write out strings */
1711
1712   if (string_size != 0)
1713    {
1714      unsigned int    size = string_size + 4;
1715      bfd_byte buffer[4];
1716
1717      bfd_h_put_32(abfd, size, buffer);
1718      bfd_write((PTR) buffer, 1, sizeof(buffer), abfd);
1719      for (p = abfd->outsymbols, i = 0;
1720           i < limit;
1721           i++, p++)
1722          {
1723            asymbol        *q = *p;
1724            size_t          name_length = strlen(q->name);
1725            int maxlen;
1726            coff_symbol_type*       c_symbol = coff_symbol_from(abfd, q);
1727            maxlen = ((c_symbol != NULL && c_symbol->native != NULL) &&
1728                      (c_symbol->native->u.syment.n_sclass == C_FILE)) ?
1729              FILNMLEN : SYMNMLEN;
1730
1731            if (name_length > maxlen) {
1732              bfd_write((PTR) (q->name), 1, name_length + 1, abfd);
1733            }
1734          }
1735    }
1736   else {
1737     /* We would normally not write anything here, but we'll write
1738        out 4 so that any stupid coff reader which tries to read
1739        the string table even when there isn't one won't croak.
1740        */
1741
1742     uint32e_type size = 4;
1743     size =  size;
1744     bfd_write((PTR)&size, 1, sizeof(size), abfd);
1745
1746   }
1747 }
1748
1749 /*doc*
1750 @subsubsection Writing Relocations
1751 To write a relocations, all the back end does is step though the
1752 canonical relocation table, and create an @code{internal_reloc}. The
1753 symbol index to use is removed from the @code{offset} field in the
1754 symbol table supplied, the address comes directly from the sum of the
1755 section base address and the relocation offset and the type is dug
1756 directly from the howto field.
1757
1758 Then the @code{internal_reloc} is swapped into the shape of an
1759 @code{external_reloc} and written out to disk.
1760 */
1761
1762 static void
1763 DEFUN(coff_write_relocs,(abfd),
1764       bfd            *abfd)
1765 {
1766   asection       *s;
1767   for (s = abfd->sections; s != (asection *) NULL; s = s->next) {
1768     unsigned int    i;
1769     struct external_reloc dst;
1770
1771     arelent       **p = s->orelocation;
1772     bfd_seek(abfd, s->rel_filepos, SEEK_SET);
1773     for (i = 0; i < s->reloc_count; i++) {
1774       struct internal_reloc    n;
1775       arelent        *q = p[i];
1776       memset((PTR)&n, 0, sizeof(n));
1777       n.r_vaddr = q->address + s->vma;
1778       if (q->sym_ptr_ptr) {
1779         n.r_symndx = get_index((*(q->sym_ptr_ptr)));
1780       }
1781 #ifdef SELECT_RELOC
1782       /* Work out reloc type from what is required */
1783       SELECT_RELOC(n.r_type, q->howto);
1784 #else
1785       n.r_type = q->howto->type;
1786 #endif
1787       coff_swap_reloc_out(abfd, &n, &dst);
1788       bfd_write((PTR) &n, 1, RELSZ, abfd);
1789     }
1790   }
1791 }
1792 #endif /* NO_COFF_SYMBOLS */
1793
1794 #ifndef NO_COFF_LINENOS
1795
1796 static void
1797 DEFUN(coff_write_linenumbers,(abfd),
1798       bfd            *abfd)
1799 {
1800   asection       *s;
1801   for (s = abfd->sections; s != (asection *) NULL; s = s->next) {
1802     if (s->lineno_count) {
1803       asymbol       **q = abfd->outsymbols;
1804       bfd_seek(abfd, s->line_filepos, SEEK_SET);
1805       /* Find all the linenumbers in this section */
1806       while (*q) {
1807         asymbol        *p = *q;
1808         alent          *l = BFD_SEND(p->the_bfd, _get_lineno, (p->the_bfd, p));
1809         if (l) {
1810           /* Found a linenumber entry, output */
1811           struct internal_lineno  out;
1812           LINENO buff;
1813           memset( (PTR)&out, 0, sizeof(out));
1814           out.l_lnno = 0;
1815           out.l_addr.l_symndx = l->u.offset;
1816           coff_swap_lineno_out(abfd, &out, &buff);
1817           bfd_write((PTR) &buff, 1, LINESZ, abfd);
1818           l++;
1819           while (l->line_number) {
1820             out.l_lnno = l->line_number;
1821             out.l_addr.l_symndx = l->u.offset;
1822             coff_swap_lineno_out(abfd, &out, &buff);
1823             bfd_write((PTR) &buff, 1, LINESZ, abfd);
1824             l++;
1825           }
1826         }
1827         q++;
1828       }
1829     }
1830   }
1831 }
1832
1833 static alent   *
1834 DEFUN(coff_get_lineno,(ignore_abfd, symbol),
1835       bfd            *ignore_abfd AND
1836       asymbol        *symbol)
1837 {
1838   return coffsymbol(symbol)->lineno;
1839 }
1840
1841 #endif /* NO_COFF_LINENOS */
1842
1843 static asymbol *
1844 coff_make_empty_symbol(abfd)
1845 bfd            *abfd;
1846 {
1847   coff_symbol_type *new = (coff_symbol_type *) bfd_alloc(abfd, sizeof(coff_symbol_type));
1848   if (new == NULL) {
1849     bfd_error = no_memory;
1850     return (NULL);
1851   }                             /* on error */
1852   new->native = 0;
1853   new->lineno = (alent *) NULL;
1854   new->symbol.the_bfd = abfd;
1855   return &new->symbol;
1856 }
1857
1858 #ifndef NO_COFF_SYMBOLS
1859
1860 static void
1861 DEFUN(coff_print_symbol,(ignore_abfd, filep, symbol, how),
1862       bfd            *ignore_abfd AND
1863       PTR           filep AND
1864       asymbol        *symbol AND
1865       bfd_print_symbol_type how)
1866 {
1867   FILE *file = (FILE *)filep;
1868   switch (how) {
1869   case bfd_print_symbol_name:
1870     fprintf(file, "%s", symbol->name);
1871     break;
1872   case bfd_print_symbol_more:
1873     fprintf(file, "coff %lx %lx", (unsigned long) coffsymbol(symbol)->native,
1874             (unsigned long) coffsymbol(symbol)->lineno);
1875     break;
1876   case bfd_print_symbol_all:
1877       {
1878         CONST char           *section_name = symbol->section == (asection *) NULL ?
1879           "*abs" : symbol->section->name;
1880         bfd_print_symbol_vandf((PTR) file, symbol);
1881
1882         fprintf(file, " %-5s %s %s %s",
1883                 section_name,
1884                 coffsymbol(symbol)->native ? "n" : "g",
1885                 coffsymbol(symbol)->lineno ? "l" : " ",
1886                 symbol->name);
1887       }
1888
1889
1890     break;
1891   }
1892 }
1893
1894 #endif /* NO_COFF_SYMBOLS */
1895
1896 /* Set flags and magic number of a coff file from architecture and machine
1897    type.  Result is true if we can represent the arch&type, false if not.  */
1898
1899 static          boolean
1900 DEFUN(coff_set_flags,(abfd, magicp, flagsp),
1901       bfd            *abfd AND
1902       unsigned       *magicp AND
1903       unsigned short *flagsp)
1904 {
1905   switch (bfd_get_arch(abfd)) {
1906
1907 #ifdef I960ROMAGIC
1908
1909   case bfd_arch_i960:
1910
1911       {
1912         unsigned        flags;
1913         *magicp = I960ROMAGIC;
1914         /*
1915           ((bfd_get_file_flags(abfd) & WP_TEXT) ? I960ROMAGIC :
1916           I960RWMAGIC);   FIXME???
1917           */
1918         switch (bfd_get_mach(abfd)) {
1919         case bfd_mach_i960_core:
1920           flags = F_I960CORE;
1921           break;
1922         case bfd_mach_i960_kb_sb:
1923           flags = F_I960KB;
1924           break;
1925         case bfd_mach_i960_mc:
1926           flags = F_I960MC;
1927           break;
1928         case bfd_mach_i960_xa:
1929           flags = F_I960XA;
1930           break;
1931         case bfd_mach_i960_ca:
1932           flags = F_I960CA;
1933           break;
1934         case bfd_mach_i960_ka_sa:
1935           flags = F_I960KA;
1936           break;
1937         default:
1938           return false;
1939         }
1940         *flagsp = flags;
1941         return true;
1942       }
1943     break;
1944 #endif
1945 #ifdef MIPS
1946   case bfd_arch_mips:
1947     *magicp = MIPS_MAGIC_2;
1948     return true;
1949     break;
1950 #endif
1951 #ifdef I386MAGIC
1952   case bfd_arch_i386:
1953     *magicp = I386MAGIC;
1954     return true;
1955 #endif
1956 #ifdef MC68MAGIC
1957   case bfd_arch_m68k:
1958     *magicp = MC68MAGIC;
1959     return true;
1960 #endif
1961
1962 #ifdef MC88MAGIC
1963   case bfd_arch_m88k:
1964     *magicp = MC88OMAGIC;
1965     return true;
1966     break;
1967 #endif
1968
1969 #ifdef A29K_MAGIC_BIG
1970   case bfd_arch_a29k:
1971     if (abfd->xvec->byteorder_big_p)
1972         *magicp = A29K_MAGIC_BIG;
1973     else
1974         *magicp = A29K_MAGIC_LITTLE;
1975     return true;
1976     break;
1977 #endif
1978
1979 #ifdef U802TOCMAGIC
1980   case bfd_arch_rs6000:
1981     *magicp = U802TOCMAGIC;
1982     break;
1983 #endif
1984
1985   default:                      /* Unknown architecture */
1986     /* return false;  -- fall through to "return false" below, to avoid
1987        "statement never reached" errors on the one below. */
1988     break;
1989   }
1990
1991   return false;
1992 }
1993
1994
1995 static          boolean
1996 DEFUN(coff_set_arch_mach,(abfd, arch, machine),
1997       bfd            *abfd AND
1998       enum bfd_architecture arch AND
1999       unsigned long   machine)
2000 {
2001   unsigned        dummy1;
2002   unsigned     short dummy2;
2003   bfd_default_set_arch_mach(abfd, arch, machine);
2004
2005   if (arch != bfd_arch_unknown &&
2006       coff_set_flags(abfd, &dummy1, &dummy2) != true)
2007     return false;               /* We can't represent this type */
2008   return true;                  /* We're easy ... */
2009 }
2010
2011
2012 /* Calculate the file position for each section. */
2013
2014 static void
2015 DEFUN(coff_compute_section_file_positions,(abfd),
2016       bfd            *abfd)
2017 {
2018   asection       *current;
2019   file_ptr        sofar = FILHSZ;
2020   if (bfd_get_start_address(abfd)) {
2021     /*
2022       A start address may have been added to the original file. In this
2023       case it will need an optional header to record it.
2024       */
2025     abfd->flags |= EXEC_P;
2026   }
2027   if (abfd->flags & EXEC_P)
2028     sofar += AOUTSZ;
2029
2030
2031   sofar += abfd->section_count * SCNHSZ;
2032   for (current = abfd->sections;
2033        current != (asection *)NULL;
2034        current = current->next) {
2035     /* Only deal with sections which have contents */
2036     if (!(current->flags & SEC_HAS_CONTENTS))
2037       continue;
2038
2039     /* Align the sections in the file to the same boundary on
2040        which they are aligned in virtual memory.  I960 doesn't
2041        do this (FIXME) so we can stay in sync with Intel.  960
2042        doesn't yet page from files... */
2043 #ifndef I960
2044    {
2045      /* Whatever the alignment, make sure that the sections are big
2046         enough to cover the gap */
2047     bfd_vma old_sofar= sofar;
2048     sofar = ALIGN(sofar, 1 << current->alignment_power);
2049     current->size += sofar - old_sofar;
2050   }
2051 #endif
2052     /* FIXME, in demand paged files, the low order bits of the file
2053        offset must match the low order bits of the virtual address.
2054        "Low order" is apparently implementation defined.  Add code
2055        here to round sofar up to match the virtual address.  */
2056
2057     current->filepos = sofar;
2058     sofar += current->size;
2059   }
2060   obj_relocbase(abfd) = sofar;
2061 }
2062
2063
2064
2065
2066 /* SUPPRESS 558 */
2067 /* SUPPRESS 529 */
2068 static          boolean
2069 DEFUN(coff_write_object_contents,(abfd),
2070       bfd            *abfd)
2071   {
2072     asection       *current;
2073     boolean         hasrelocs = false;
2074     boolean         haslinno = false;
2075     file_ptr        reloc_base;
2076     file_ptr        lineno_base;
2077     file_ptr        sym_base;
2078     file_ptr        scn_base;
2079     file_ptr        data_base;
2080     unsigned long   reloc_size = 0;
2081     unsigned long   lnno_size = 0;
2082     asection       *text_sec = NULL;
2083     asection       *data_sec = NULL;
2084     asection       *bss_sec = NULL;
2085
2086     struct internal_filehdr internal_f;
2087     struct internal_aouthdr internal_a;
2088
2089
2090     bfd_error = system_call_error;
2091
2092
2093     if(abfd->output_has_begun == false) {
2094       coff_compute_section_file_positions(abfd);
2095     }
2096
2097     if (abfd->sections != (asection *)NULL) {
2098       scn_base = abfd->sections->filepos;
2099   }
2100   else {
2101     scn_base = 0;
2102   }
2103   if (bfd_seek(abfd, scn_base, SEEK_SET) != 0)
2104     return false;
2105   reloc_base = obj_relocbase(abfd);
2106
2107   /* Make a pass through the symbol table to count line number entries and
2108      put them into the correct asections */
2109
2110 #ifndef NO_COFF_LINENOS
2111   coff_count_linenumbers(abfd);
2112 #endif
2113   data_base = scn_base;
2114
2115   /* Work out the size of the reloc and linno areas */
2116
2117   for (current = abfd->sections; current != NULL; current = current->next) {
2118     reloc_size += current->reloc_count * RELSZ;
2119 #ifndef NO_COFF_LINENOS
2120     lnno_size += current->lineno_count * LINESZ;
2121 #endif
2122     data_base += SCNHSZ;
2123   }
2124
2125   lineno_base = reloc_base + reloc_size;
2126   sym_base = lineno_base + lnno_size;
2127
2128   /* Indicate in each section->line_filepos its actual file address */
2129   for (current = abfd->sections; current != NULL; current = current->next) {
2130     if (current->lineno_count) {
2131       current->line_filepos = lineno_base;
2132       current->moving_line_filepos = lineno_base;
2133 #ifndef NO_COFF_LINENOS
2134       lineno_base += current->lineno_count * LINESZ;
2135 #endif
2136     }
2137     else {
2138       current->line_filepos = 0;
2139     }
2140     if (current->reloc_count) {
2141       current->rel_filepos = reloc_base;
2142       reloc_base += current->reloc_count * sizeof(struct internal_reloc);
2143     }
2144     else {
2145       current->rel_filepos = 0;
2146     }
2147   }
2148
2149   /* Write section headers to the file.  */
2150
2151   bfd_seek(abfd,
2152            (file_ptr) ((abfd->flags & EXEC_P) ?
2153                        (FILHSZ + AOUTSZ) : FILHSZ),
2154            SEEK_SET);
2155
2156     {
2157 #if 0
2158       unsigned int    pad = abfd->flags & D_PAGED ? data_base : 0;
2159 #endif
2160       unsigned int    pad = 0;
2161
2162       for (current = abfd->sections; current != NULL; current = current->next) {
2163         struct internal_scnhdr section;
2164         strncpy(&(section.s_name[0]), current->name, 8);
2165         section.s_vaddr = current->vma + pad;
2166         section.s_paddr = current->vma + pad;
2167         section.s_size = current->size - pad;
2168         /*
2169           If this section has no size or is unloadable then the scnptr
2170           will be 0 too
2171           */
2172         if (current->size - pad == 0 ||
2173             (current->flags & SEC_LOAD) == 0) {
2174           section.s_scnptr = 0;
2175         }
2176         else {
2177           section.s_scnptr = current->filepos;
2178         }
2179         section.s_relptr = current->rel_filepos;
2180         section.s_lnnoptr = current->line_filepos;
2181         section.s_nreloc = current->reloc_count;
2182         section.s_nlnno = current->lineno_count;
2183         if (current->reloc_count != 0)
2184           hasrelocs = true;
2185         if (current->lineno_count != 0)
2186           haslinno = true;
2187
2188         section.s_flags = sec_to_styp_flags(current->name,current->flags);
2189
2190         if (!strcmp(current->name, _TEXT)) {
2191           text_sec = current;
2192         } else if (!strcmp(current->name, _DATA)) {
2193           data_sec = current;
2194         } else if (!strcmp(current->name, _BSS)) {
2195           bss_sec = current;
2196         }
2197
2198 #ifdef I960
2199         section.s_align = (current->alignment_power
2200                            ? 1 << current->alignment_power
2201                            : 0);
2202
2203 #endif
2204           {
2205             SCNHDR          buff;
2206
2207             coff_swap_scnhdr_out(abfd, &section, &buff);
2208             bfd_write((PTR) (&buff), 1, SCNHSZ, abfd);
2209
2210           }
2211         pad = 0;
2212       }
2213     }
2214
2215   /* OK, now set up the filehdr... */
2216   internal_f.f_nscns = abfd->section_count;
2217   /*
2218     We will NOT put a fucking timestamp in the header here. Every time you
2219     put it back, I will come in and take it out again. I'm sorry. This
2220     field does not belong here.  We fill it with a 0 so it compares the
2221     same but is not a reasonable time. -- gnu@cygnus.com
2222     */
2223   /*
2224     Well, I like it, so I'm conditionally compiling it in.
2225     steve@cygnus.com
2226     */
2227 #ifdef COFF_TIMESTAMP
2228   internal_f.f_timdat = time(0);
2229 #else
2230   internal_f.f_timdat = 0;
2231 #endif
2232
2233   if (bfd_get_symcount(abfd) != 0)
2234     internal_f.f_symptr = sym_base;
2235   else
2236     internal_f.f_symptr = 0;
2237
2238   internal_f.f_flags = 0;
2239
2240   if (abfd->flags & EXEC_P)
2241     internal_f.f_opthdr = AOUTSZ;
2242   else
2243     internal_f.f_opthdr = 0;
2244
2245   if (!hasrelocs)
2246     internal_f.f_flags |= F_RELFLG;
2247   if (!haslinno)
2248     internal_f.f_flags |= F_LNNO;
2249   if (0 == bfd_get_symcount(abfd))
2250     internal_f.f_flags |= F_LSYMS;
2251   if (abfd->flags & EXEC_P)
2252     internal_f.f_flags |= F_EXEC;
2253 #if M88
2254   internal_f.f_flags |= F_AR32W;
2255 #else
2256   if (!abfd->xvec->byteorder_big_p)
2257     internal_f.f_flags |= F_AR32WR;
2258 #endif
2259   /*
2260     FIXME, should do something about the other byte orders and
2261     architectures.
2262     */
2263
2264   /* Set up architecture-dependent stuff */
2265
2266     { unsigned int   magic = 0;
2267       unsigned short    flags = 0;
2268       coff_set_flags(abfd, &magic, &flags);
2269       internal_f.f_magic = magic;
2270       internal_f.f_flags |= flags;
2271       /* ...and the "opt"hdr... */
2272
2273 #ifdef A29K
2274 # ifdef ULTRA3  /* NYU's machine */
2275         /* FIXME: This is a bogus check.  I really want to see if there
2276          * is a .shbss or a .shdata section, if so then set the magic
2277          * number to indicate a shared data executable.
2278          */
2279       if (internal_f.f_nscns >= 7)
2280         internal_a.magic = SHMAGIC;     /* Shared magic */
2281       else
2282 # endif /* ULTRA3 */
2283         internal_a.magic = NMAGIC;      /* Assume separate i/d */
2284 #define __A_MAGIC_SET__
2285 #endif  /* A29K */
2286 #ifdef I960
2287       internal_a.magic = (magic == I960ROMAGIC ? NMAGIC : OMAGIC);
2288 #define __A_MAGIC_SET__
2289 #endif  /* I960 */
2290 #if M88
2291 #define __A_MAGIC_SET__
2292       internal_a.magic = PAGEMAGICBCS;
2293 #endif  /* M88 */
2294
2295 #if M68 || I386 || MIPS
2296 #define __A_MAGIC_SET__
2297      /* Never was anything here for the 68k */
2298 #endif  /* M88 */
2299
2300 #if RS6000COFF_C
2301 #define __A_MAGIC_SET__
2302       internal_a.magic = (abfd->flags & D_PAGED)? RS6K_AOUTHDR_ZMAGIC:
2303                          (abfd->flags & WP_TEXT)? RS6K_AOUTHDR_NMAGIC:
2304                                                   RS6K_AOUTHDR_OMAGIC;
2305 #endif
2306
2307 #ifndef __A_MAGIC_SET__
2308 # include "Your aouthdr magic number is not being set!"
2309 #else
2310 # undef __A_MAGIC_SET__
2311 #endif
2312     }
2313   /* Now should write relocs, strings, syms */
2314   obj_sym_filepos(abfd) = sym_base;
2315
2316 #ifndef NO_COFF_SYMBOLS
2317   if (bfd_get_symcount(abfd) != 0) {
2318     coff_renumber_symbols(abfd);
2319     coff_mangle_symbols(abfd);
2320     coff_write_symbols(abfd);
2321     coff_write_linenumbers(abfd);
2322     coff_write_relocs(abfd);
2323   }
2324 #endif /* NO_COFF_SYMBOLS */
2325   if (text_sec) {
2326     internal_a.tsize = text_sec->size;
2327     internal_a.text_start =text_sec->size ? text_sec->vma : 0;
2328   }
2329   if (data_sec) {
2330     internal_a.dsize = data_sec->size;
2331     internal_a.data_start = data_sec->size ? data_sec->vma      : 0;
2332   }
2333   if (bss_sec) {
2334     internal_a.bsize =  bss_sec->size;
2335   }
2336
2337   internal_a.entry = bfd_get_start_address(abfd);
2338   internal_f.f_nsyms =  bfd_get_symcount(abfd);
2339
2340   /* now write them */
2341   if (bfd_seek(abfd, 0L, SEEK_SET) != 0)
2342     return false;
2343     {
2344       FILHDR buff;
2345       coff_swap_filehdr_out(abfd, &internal_f, &buff);
2346       bfd_write((PTR) &buff, 1, FILHSZ, abfd);
2347     }
2348   if (abfd->flags & EXEC_P) {
2349     AOUTHDR buff;
2350     coff_swap_aouthdr_out(abfd, &internal_a, &buff);
2351     bfd_write((PTR) &buff, 1, AOUTSZ, abfd);
2352   }
2353   return true;
2354 }
2355
2356 #ifndef NO_COFF_SYMBOLS
2357
2358 /*
2359 this function transforms the offsets into the symbol table into
2360 pointers to syments.
2361 */
2362
2363
2364 static void
2365 DEFUN(coff_pointerize_aux,(ignore_abfd, table_base, type, class, auxent),
2366 bfd *ignore_abfd AND
2367 combined_entry_type *table_base AND
2368 int type AND
2369 int class AND
2370 combined_entry_type *auxent)
2371 {
2372   /* Don't bother if this is a file or a section */
2373   if (class == C_STAT && type == T_NULL) return;
2374   if (class == C_FILE) return;
2375
2376   /* Otherwise patch up */
2377   if (ISFCN(type) || ISTAG(class) || class == C_BLOCK) {
2378     auxent->u.auxent.x_sym.x_fcnary.x_fcn.x_endndx.p = table_base +
2379       auxent->u.auxent.x_sym.x_fcnary.x_fcn.x_endndx.l;
2380     auxent->fix_end = 1;
2381   }
2382   if (auxent->u.auxent.x_sym.x_tagndx.l != 0) {
2383     auxent->u.auxent.x_sym.x_tagndx.p = table_base +  auxent->u.auxent.x_sym.x_tagndx.l;
2384     auxent->fix_tag = 1;
2385   }
2386 }
2387
2388 #endif /* NO_COFF_SYMBOLS */
2389
2390 static          boolean
2391 DEFUN(coff_set_section_contents,(abfd, section, location, offset, count),
2392       bfd            *abfd AND
2393       sec_ptr         section AND
2394       PTR             location AND
2395       file_ptr        offset AND
2396       bfd_size_type   count)
2397 {
2398     if (abfd->output_has_begun == false)        /* set by bfd.c handler */
2399         coff_compute_section_file_positions(abfd);
2400
2401     bfd_seek(abfd, (file_ptr) (section->filepos + offset), SEEK_SET);
2402
2403     if (count != 0) {
2404         return (bfd_write(location, 1, count, abfd) == count) ? true : false;
2405     }
2406     return true;
2407 }
2408 #if 0
2409 static          boolean
2410 coff_close_and_cleanup(abfd)
2411     bfd            *abfd;
2412 {
2413   if (!bfd_read_p(abfd))
2414     switch (abfd->format) {
2415     case bfd_archive:
2416       if (!_bfd_write_archive_contents(abfd))
2417         return false;
2418       break;
2419     case bfd_object:
2420       if (!coff_write_object_contents(abfd))
2421         return false;
2422       break;
2423     default:
2424       bfd_error = invalid_operation;
2425       return false;
2426     }
2427
2428   /* We depend on bfd_close to free all the memory on the obstack.  */
2429   /* FIXME if bfd_release is not using obstacks! */
2430   return true;
2431 }
2432
2433 #endif
2434 static PTR
2435 buy_and_read(abfd, where, seek_direction, size)
2436     bfd            *abfd;
2437     file_ptr        where;
2438     int             seek_direction;
2439     size_t          size;
2440 {
2441     PTR             area = (PTR) bfd_alloc(abfd, size);
2442     if (!area) {
2443         bfd_error = no_memory;
2444         return (NULL);
2445     }
2446     bfd_seek(abfd, where, seek_direction);
2447     if (bfd_read(area, 1, size, abfd) != size) {
2448         bfd_error = system_call_error;
2449         return (NULL);
2450     }                           /* on error */
2451     return (area);
2452 }                               /* buy_and_read() */
2453
2454
2455 #ifndef NO_COFF_SYMBOLS
2456
2457 static char *
2458 DEFUN(build_string_table,(abfd),
2459 bfd *abfd)
2460 {
2461   char string_table_size_buffer[4];
2462   unsigned int string_table_size;
2463   char *string_table;
2464
2465   /* At this point we should be "seek"'d to the end of the
2466      symbols === the symbol table size.  */
2467   if (bfd_read((char *) string_table_size_buffer,
2468                sizeof(string_table_size_buffer),
2469                1, abfd) != sizeof(string_table_size)) {
2470     bfd_error = system_call_error;
2471     return (NULL);
2472   }                             /* on error */
2473
2474   string_table_size = bfd_h_get_32(abfd, (bfd_byte *) string_table_size_buffer);
2475
2476   if ((string_table = (PTR) bfd_alloc(abfd, string_table_size -= 4)) == NULL) {
2477     bfd_error = no_memory;
2478     return (NULL);
2479   }                             /* on mallocation error */
2480   if (bfd_read(string_table, string_table_size, 1, abfd) != string_table_size) {
2481     bfd_error = system_call_error;
2482     return (NULL);
2483   }
2484   return string_table;
2485 }
2486
2487 /* Allocate space for the ".debug" section, and read it.
2488    We did not read the debug section until now, because
2489    we didn't want to go to the trouble until someone needed it. */
2490
2491 static char *
2492 DEFUN(build_debug_section,(abfd),
2493         bfd *abfd)
2494 {
2495   char *debug_section;
2496   long position;
2497
2498   asection *sect = bfd_get_section_by_name (abfd, ".debug");
2499
2500   if (!sect) {
2501      bfd_error = no_debug_section;
2502      return NULL;
2503   }
2504
2505   debug_section = (PTR) bfd_alloc (abfd, bfd_section_size (abfd, sect));
2506   if (debug_section == NULL) {
2507     bfd_error = no_memory;
2508     return NULL;
2509   }
2510
2511   /* Seek to the beginning of the `.debug' section and read it. 
2512      Save the current position first; it is needed by our caller.
2513      Then read debug section and reset the file pointer.  */
2514
2515   position = bfd_tell (abfd);
2516   bfd_seek (abfd, sect->filepos, SEEK_SET);
2517   if (bfd_read (debug_section, bfd_section_size (abfd, sect), 1, abfd)
2518       != bfd_section_size (abfd, sect)) {
2519     bfd_error = system_call_error;
2520     return NULL;
2521   }
2522   bfd_seek (abfd, position, SEEK_SET);
2523   return debug_section;
2524 }
2525
2526
2527 /* Return a pointer to a malloc'd copy of 'name'.  'name' may not be
2528  \0-terminated, but will not exceed 'maxlen' characters.  The copy *will*
2529  be \0-terminated.  */
2530 static char *
2531 DEFUN(copy_name,(abfd, name, maxlen),
2532       bfd *abfd AND
2533       char *name AND
2534       int maxlen)
2535 {
2536   int  len;
2537   char *newname;
2538
2539   for (len = 0; len < maxlen; ++len) {
2540     if (name[len] == '\0') {
2541       break;
2542     }
2543   }
2544
2545   if ((newname = (PTR) bfd_alloc(abfd, len+1)) == NULL) {
2546     bfd_error = no_memory;
2547     return (NULL);
2548   }
2549   strncpy(newname, name, len);
2550   newname[len] = '\0';
2551   return newname;
2552 }
2553
2554
2555 /* Read a symbol table into freshly bfd_allocated memory, swap it, and
2556    knit the symbol names into a normalized form.  By normalized here I
2557    mean that all symbols have an n_offset pointer that points to a null-
2558    terminated string.  */
2559
2560 #ifndef SYMNAME_IN_DEBUG
2561 #define SYMNAME_IN_DEBUG(x)  0
2562 #endif
2563
2564 static combined_entry_type *
2565 DEFUN(get_normalized_symtab,(abfd),
2566 bfd            *abfd)
2567 {
2568   combined_entry_type          *internal;
2569   combined_entry_type          *internal_ptr;
2570   combined_entry_type         *internal_end;
2571   SYMENT *raw;
2572   SYMENT *raw_src;
2573   SYMENT *raw_end;
2574   char           *string_table = NULL;
2575   char           *debug_section = NULL;
2576   unsigned long   size;
2577
2578   unsigned int raw_size;
2579   if (obj_raw_syments(abfd) != (combined_entry_type *)NULL) {
2580     return obj_raw_syments(abfd);
2581   }
2582   if ((size = bfd_get_symcount(abfd) * sizeof(combined_entry_type)) == 0) {
2583     bfd_error = no_symbols;
2584     return (NULL);
2585   }
2586
2587   internal = (combined_entry_type *)bfd_alloc(abfd, size);
2588   internal_end = internal + bfd_get_symcount(abfd);
2589
2590   raw_size =      bfd_get_symcount(abfd) * SYMESZ;
2591   raw = (SYMENT *)bfd_alloc(abfd,raw_size);
2592
2593   if (bfd_seek(abfd, obj_sym_filepos(abfd), SEEK_SET) == -1
2594       || bfd_read((PTR)raw, raw_size, 1, abfd) != raw_size) {
2595     bfd_error = system_call_error;
2596     return (NULL);
2597   }
2598   /* mark the end of the symbols */
2599   raw_end = raw + bfd_get_symcount(abfd);
2600   /*
2601     FIXME SOMEDAY.  A string table size of zero is very weird, but
2602     probably possible.  If one shows up, it will probably kill us.
2603     */
2604
2605   /* Swap all the raw entries */
2606   for (raw_src = raw, internal_ptr = internal;
2607        raw_src < raw_end;
2608        raw_src++, internal_ptr++) {
2609
2610     unsigned int i;
2611     coff_swap_sym_in(abfd, (char *)raw_src, (char *)&internal_ptr->u.syment);
2612     internal_ptr->fix_tag = 0;
2613     internal_ptr->fix_end = 0;
2614
2615     for (i = internal_ptr->u.syment.n_numaux;
2616          i;
2617          --i, raw_src++, internal_ptr++) {
2618
2619       (internal_ptr+1)->fix_tag = 0;
2620       (internal_ptr+1)->fix_end = 0;
2621
2622       coff_swap_aux_in(abfd, (char *)(raw_src +1),
2623                        internal_ptr->u.syment.n_type,
2624                        internal_ptr->u.syment.n_sclass,
2625                        &(internal_ptr+1)->u.auxent);
2626
2627       coff_pointerize_aux(abfd,
2628                           internal,
2629                           internal_ptr->u.syment.n_type,
2630                           internal_ptr->u.syment.n_sclass,
2631                           internal_ptr +1);
2632     }
2633   }
2634
2635   /* Free all the raw stuff */
2636   bfd_release(abfd, raw);
2637
2638   for (internal_ptr = internal; internal_ptr < internal_end;
2639        internal_ptr ++)
2640       {
2641         if (internal_ptr->u.syment.n_sclass == C_FILE) {
2642           /* make a file symbol point to the name in the auxent, since
2643              the text ".file" is redundant */
2644           if ((internal_ptr+1)->u.auxent.x_file.x_n.x_zeroes == 0) {
2645             /* the filename is a long one, point into the string table */
2646             if (string_table == NULL) {
2647               string_table = build_string_table(abfd);
2648             }
2649
2650             internal_ptr->u.syment._n._n_n._n_offset =
2651               (int) (string_table - 4 +
2652                      (internal_ptr+1)->u.auxent.x_file.x_n.x_offset);
2653           }
2654           else {
2655             /* ordinary short filename, put into memory anyway */
2656             internal_ptr->u.syment._n._n_n._n_offset = (int)
2657               copy_name(abfd, (internal_ptr+1)->u.auxent.x_file.x_fname,
2658                         FILNMLEN);
2659           }
2660         }
2661         else {
2662           if (internal_ptr->u.syment._n._n_n._n_zeroes != 0) {
2663             /* This is a "short" name.  Make it long.  */
2664             unsigned long   i = 0;
2665             char           *newstring = NULL;
2666
2667             /* find the length of this string without walking into memory
2668                that isn't ours.  */
2669             for (i = 0; i < 8; ++i) {
2670               if (internal_ptr->u.syment._n._n_name[i] == '\0') {
2671                 break;
2672               }                 /* if end of string */
2673             }                   /* possible lengths of this string. */
2674
2675             if ((newstring = (PTR) bfd_alloc(abfd, ++i)) == NULL) {
2676               bfd_error = no_memory;
2677               return (NULL);
2678             }                   /* on error */
2679             bzero(newstring, i);
2680             strncpy(newstring, internal_ptr->u.syment._n._n_name, i-1);
2681             internal_ptr->u.syment._n._n_n._n_offset =  (int) newstring;
2682             internal_ptr->u.syment._n._n_n._n_zeroes = 0;
2683           }
2684           else if (!SYMNAME_IN_DEBUG(&internal_ptr->u.syment)) {
2685             /* Long name already.  Point symbol at the string in the table.  */
2686             if (string_table == NULL) {
2687               string_table = build_string_table(abfd);
2688             }
2689             internal_ptr->u.syment._n._n_n._n_offset = (int)
2690               (string_table - 4 + internal_ptr->u.syment._n._n_n._n_offset);
2691           }
2692           else {
2693             /* Long name in debug section.  Very similar.  */
2694             if (debug_section == NULL) {
2695               debug_section = build_debug_section(abfd);
2696             }
2697             internal_ptr->u.syment._n._n_n._n_offset = (int)
2698               (debug_section + internal_ptr->u.syment._n._n_n._n_offset);
2699           }
2700         }
2701         internal_ptr += internal_ptr->u.syment.n_numaux;
2702       }
2703
2704   obj_raw_syments(abfd) = internal;
2705
2706   return (internal);
2707 }                               /* get_normalized_symtab() */
2708
2709 #endif /* NO_COFF_SYMBOLS */
2710
2711 static
2712 struct sec *
2713 DEFUN(section_from_bfd_index,(abfd, index),
2714       bfd            *abfd AND
2715       int             index)
2716 {
2717   if (index > 0) {
2718     struct sec *answer = abfd->sections;
2719     while (--index) {
2720       answer = answer->next;
2721     }
2722     return answer;
2723   }
2724   return 0;
2725 }
2726
2727 #ifndef NO_COFF_LINENOS
2728
2729 /*doc*
2730 @subsubsection Reading Linenumbers
2731 Createing the linenumber table is done by reading in the entire coff
2732 linenumber table, and creating another table for internal use.
2733
2734 A coff line number table is structured so that each
2735 function is marked as having a line number of 0. Each line within the
2736 function is an offset from the first line in the function. The base of
2737 the line number information for the table is stored in the symbol
2738 associated with the function.
2739
2740 The information is copied from the external to the internal table, and
2741 each symbol which marks a function is marked by pointing its...
2742
2743 **How does this work ?**
2744
2745 */
2746
2747 static boolean
2748 coff_slurp_line_table(abfd, asect)
2749 bfd            *abfd;
2750 asection       *asect;
2751   {
2752     LINENO  *native_lineno;
2753     alent          *lineno_cache;
2754
2755     BFD_ASSERT(asect->lineno == (alent *) NULL);
2756
2757     native_lineno = (LINENO *) buy_and_read(abfd,
2758                                             asect->line_filepos,
2759                                             SEEK_SET,
2760                                             (size_t) (LINESZ *
2761                                                       asect->lineno_count));
2762     lineno_cache =
2763       (alent *) bfd_alloc(abfd, (size_t) ((asect->lineno_count + 1) * sizeof(alent)));
2764     if (lineno_cache == NULL) {
2765       bfd_error = no_memory;
2766       return false;
2767     } else {
2768       unsigned int    counter = 0;
2769       alent          *cache_ptr = lineno_cache;
2770       LINENO  *src = native_lineno;
2771
2772       while (counter < asect->lineno_count) {
2773         struct internal_lineno dst;
2774         coff_swap_lineno_in(abfd, src, &dst);
2775         cache_ptr->line_number = dst.l_lnno;
2776
2777         if (cache_ptr->line_number == 0) {
2778           coff_symbol_type *sym =
2779             (coff_symbol_type *) (dst.l_addr.l_symndx
2780                                   + obj_symbol_slew(abfd)
2781                                   + obj_raw_syments(abfd))->u.syment._n._n_n._n_zeroes;
2782           cache_ptr->u.sym = (asymbol *) sym;
2783           sym->lineno = cache_ptr;
2784         }
2785         else {
2786           cache_ptr->u.offset = dst.l_addr.l_paddr
2787             - bfd_section_vma(abfd, asect);
2788         }                               /* If no linenumber expect a symbol index */
2789
2790         cache_ptr++;
2791         src++;
2792         counter++;
2793       }
2794       cache_ptr->line_number = 0;
2795
2796     }
2797     asect->lineno = lineno_cache;
2798     /* FIXME, free native_lineno here, or use alloca or something. */
2799     return true;
2800   }                             /* coff_slurp_line_table() */
2801
2802 #endif /* NO_COFF_LINENOS */
2803
2804 #ifndef NO_COFF_LINENOS
2805
2806 static          boolean
2807 DEFUN(coff_slurp_symbol_table,(abfd),
2808       bfd            *abfd)
2809 {
2810   combined_entry_type         *native_symbols;
2811   coff_symbol_type *cached_area;
2812   unsigned int   *table_ptr;
2813
2814   unsigned int    number_of_symbols = 0;
2815   if (obj_symbols(abfd))
2816     return true;
2817   bfd_seek(abfd, obj_sym_filepos(abfd), SEEK_SET);
2818
2819   /* Read in the symbol table */
2820   if ((native_symbols = get_normalized_symtab(abfd)) == NULL) {
2821     return (false);
2822   }                             /* on error */
2823
2824   /* Allocate enough room for all the symbols in cached form */
2825   cached_area =
2826     (coff_symbol_type *)
2827       bfd_alloc(abfd, (size_t) (bfd_get_symcount(abfd) * sizeof(coff_symbol_type)));
2828
2829   if (cached_area == NULL) {
2830     bfd_error = no_memory;
2831     return false;
2832   }                             /* on error */
2833   table_ptr =
2834     (unsigned int *)
2835       bfd_alloc(abfd, (size_t) (bfd_get_symcount(abfd) * sizeof(unsigned int)));
2836
2837   if (table_ptr == NULL) {
2838     bfd_error = no_memory;
2839     return false;
2840   } else {
2841     coff_symbol_type *dst = cached_area;
2842     unsigned int    last_native_index = bfd_get_symcount(abfd);
2843     unsigned int    this_index = 0;
2844     while (this_index < last_native_index) {
2845       combined_entry_type         *src = native_symbols + this_index;
2846       table_ptr[this_index] = number_of_symbols;
2847       dst->symbol.the_bfd = abfd;
2848
2849       dst->symbol.name = (char *)(src->u.syment._n._n_n._n_offset);
2850       /*
2851         We use the native name field to point to the cached field
2852         */
2853       src->u.syment._n._n_n._n_zeroes = (int) dst;
2854       dst->symbol.section = section_from_bfd_index(abfd,
2855                                                    src->u.syment.n_scnum);
2856       switch (src->u.syment.n_sclass) {
2857 #ifdef I960
2858       case C_LEAFEXT:
2859 #if 0
2860         dst->symbol.value = src->u.syment.n_value - dst->symbol.section->vma;
2861         dst->symbol.flags = BSF_EXPORT | BSF_GLOBAL;
2862         dst->symbol.flags |= BSF_NOT_AT_END;
2863 #endif
2864         /* Fall through to next case */
2865
2866 #endif
2867
2868       case C_EXT:
2869 #ifdef RS6000COFF_C
2870       case C_HIDEXT:
2871 #endif
2872         if ((src->u.syment.n_scnum) == 0) {
2873           if ((src->u.syment.n_value) == 0) {
2874             dst->symbol.flags = BSF_UNDEFINED;
2875             dst->symbol.value= 0;
2876           }
2877           else {
2878             dst->symbol.flags = BSF_FORT_COMM;
2879             dst->symbol.value = (src->u.syment.n_value);
2880           }
2881         }
2882         else {
2883           /*
2884             Base the value as an index from the base of the
2885             section
2886             */
2887           if (dst->symbol.section == (asection *) NULL) {
2888             dst->symbol.flags = BSF_EXPORT | BSF_GLOBAL | BSF_ABSOLUTE;
2889             dst->symbol.value = src->u.syment.n_value;
2890           }
2891           else {
2892             dst->symbol.flags = BSF_EXPORT | BSF_GLOBAL;
2893             dst->symbol.value = src->u.syment.n_value - dst->symbol.section->vma;
2894           }
2895           if (ISFCN((src->u.syment.n_type))) {
2896             /*
2897               A function ext does not go at the end of a file
2898               */
2899             dst->symbol.flags |= BSF_NOT_AT_END;
2900           }
2901         }
2902         break;
2903
2904       case C_STAT:              /* static                        */
2905 #ifdef I960
2906       case C_LEAFSTAT:          /* static leaf procedure        */
2907 #endif
2908       case C_LABEL:             /* label                         */
2909         if (src->u.syment.n_scnum == -2)
2910           dst->symbol.flags = BSF_DEBUGGING;
2911         else
2912           dst->symbol.flags = BSF_LOCAL;
2913         /*
2914           Base the value as an index from the base of the section, if
2915           there is one
2916           */
2917         if (dst->symbol.section)
2918           dst->symbol.value = (src->u.syment.n_value) -
2919             dst->symbol.section->vma;
2920         else
2921           dst->symbol.value = (src->u.syment.n_value) ;
2922         break;
2923
2924       case C_MOS:               /* member of structure   */
2925       case C_EOS:               /* end of structure              */
2926 #ifdef NOTDEF   /* C_AUTOARG has the same value */
2927 #ifdef C_GLBLREG
2928       case C_GLBLREG:           /* A29k-specific storage class */
2929 #endif
2930 #endif
2931       case C_REGPARM:           /* register parameter            */
2932       case C_REG:               /* register variable             */
2933 #ifdef C_AUTOARG
2934       case C_AUTOARG:           /* 960-specific storage class */
2935 #endif
2936       case C_TPDEF:             /* type definition               */
2937       case C_ARG:
2938       case C_AUTO:              /* automatic variable */
2939       case C_FIELD:             /* bit field */
2940       case C_ENTAG:             /* enumeration tag               */
2941       case C_MOE:               /* member of enumeration         */
2942       case C_MOU:               /* member of union               */
2943       case C_UNTAG:             /* union tag                     */
2944         dst->symbol.flags = BSF_DEBUGGING;
2945         dst->symbol.value = (src->u.syment.n_value);
2946         break;
2947
2948       case C_FILE:              /* file name                     */
2949       case C_STRTAG:            /* structure tag                 */
2950 #ifdef RS6000COFF_C
2951       case C_BINCL:             /* beginning of include file     */
2952       case C_EINCL:             /* ending of include file        */
2953       case C_GSYM:
2954       case C_LSYM:
2955       case C_PSYM:
2956       case C_RSYM:
2957       case C_RPSYM:
2958       case C_STSYM:
2959       case C_DECL:
2960       case C_ENTRY:
2961       case C_FUN:
2962       case C_BSTAT:
2963       case C_ESTAT:
2964 #endif
2965         dst->symbol.flags = BSF_DEBUGGING;
2966         dst->symbol.value = (src->u.syment.n_value);
2967         break;
2968
2969       case C_BLOCK:             /* ".bb" or ".eb"                */
2970       case C_FCN:               /* ".bf" or ".ef"                */
2971       case C_EFCN:              /* physical end of function      */
2972         dst->symbol.flags = BSF_LOCAL;
2973         /*
2974           Base the value as an index from the base of the section
2975           */
2976         dst->symbol.value = (src->u.syment.n_value) - dst->symbol.section->vma;
2977         break;
2978
2979       case C_NULL:
2980       case C_EXTDEF:            /* external definition           */
2981       case C_ULABEL:            /* undefined label               */
2982       case C_USTATIC:           /* undefined static              */
2983       case C_LINE:              /* line # reformatted as symbol table entry */
2984       case C_ALIAS:             /* duplicate tag                 */
2985       case C_HIDDEN:            /* ext symbol in dmert public lib */
2986       default:
2987
2988         fprintf(stderr,"Unrecognized storage class %d\n",
2989                                 src->u.syment.n_sclass);
2990         abort();
2991         dst->symbol.flags = BSF_DEBUGGING;
2992         dst->symbol.value = (src->u.syment.n_value);
2993         break;
2994       }
2995
2996       BFD_ASSERT(dst->symbol.flags != 0);
2997
2998       dst->native = src;
2999
3000       dst->symbol.udata = 0;
3001       dst->lineno = (alent *) NULL;
3002       this_index += (src->u.syment.n_numaux) + 1;
3003       dst++;
3004       number_of_symbols++;
3005     }                           /* walk the native symtab */
3006   }                             /* bfdize the native symtab */
3007
3008   obj_symbols(abfd) = cached_area;
3009   obj_raw_syments(abfd) = native_symbols;
3010
3011   bfd_get_symcount(abfd) = number_of_symbols;
3012   obj_convert(abfd) = table_ptr;
3013   /* Slurp the line tables for each section too */
3014     {
3015       asection       *p;
3016       p = abfd->sections;
3017       while (p) {
3018         coff_slurp_line_table(abfd, p);
3019         p = p->next;
3020       }
3021     }
3022   return true;
3023 }                               /* coff_slurp_symbol_table() */
3024
3025 static unsigned int
3026 coff_get_symtab_upper_bound(abfd)
3027 bfd            *abfd;
3028   {
3029     if (!coff_slurp_symbol_table(abfd))
3030       return 0;
3031
3032     return (bfd_get_symcount(abfd) + 1) * (sizeof(coff_symbol_type *));
3033   }
3034
3035
3036 static unsigned int
3037 coff_get_symtab(abfd, alocation)
3038 bfd            *abfd;
3039 asymbol       **alocation;
3040   {
3041     unsigned int    counter = 0;
3042     coff_symbol_type *symbase;
3043     coff_symbol_type **location = (coff_symbol_type **) (alocation);
3044     if (!coff_slurp_symbol_table(abfd))
3045       return 0;
3046
3047     for (symbase = obj_symbols(abfd); counter++ < bfd_get_symcount(abfd);)
3048       *(location++) = symbase++;
3049     *location++ = 0;
3050     return bfd_get_symcount(abfd);
3051   }
3052
3053 #endif /* NO_COFF_SYMBOLS */
3054
3055 static unsigned int
3056 coff_get_reloc_upper_bound(abfd, asect)
3057 bfd            *abfd;
3058 sec_ptr         asect;
3059   {
3060     if (bfd_get_format(abfd) != bfd_object) {
3061       bfd_error = invalid_operation;
3062       return 0;
3063     }
3064     return (asect->reloc_count + 1) * sizeof(arelent *);
3065   }
3066
3067 /*doc*
3068 @subsubsection Reading Relocations
3069 Coff relocations are easily transformed into the internal BFD form
3070 (@code{arelent}).
3071
3072 Reading a coff relocation table is done in the following stages:
3073 @itemize @bullet
3074 @item
3075 The entire coff relocation table is read into memory.
3076 @item
3077 Each relocation is processed in turn, first it is swapped from the
3078 external to the internal form.
3079 @item
3080 The symbol referenced in the relocation's symbol index is turned into
3081 a pointer into the canonical symbol table. Note that this table is the
3082 same as the one returned by a call to @code{bfd_canonicalize_symtab}.
3083 The back end will call the routine and save the result if a
3084 canonicalization hasn't been done.
3085 @item
3086 The reloc index is turned into a pointer to a howto structure, in a
3087 back end specific way. For instance, the 386 and 960 use the
3088 @code{r_type} to directly produce an index into a howto table vector;
3089 the 88k subtracts a number from the @code{r_type} field and creates an
3090 addend field.
3091 @end itemize
3092 */
3093
3094 static          boolean
3095 DEFUN(coff_slurp_reloc_table,(abfd, asect, symbols),
3096       bfd            *abfd AND
3097       sec_ptr         asect AND
3098       asymbol       **symbols)
3099   {
3100     RELOC   *native_relocs;
3101     arelent        *reloc_cache;
3102     if (asect->relocation)
3103       return true;
3104     if (asect->reloc_count == 0)
3105       return true;
3106 #ifndef NO_COFF_SYMBOLS
3107     if (!coff_slurp_symbol_table(abfd))
3108       return false;
3109 #endif
3110     native_relocs =
3111       (RELOC *) buy_and_read(abfd,
3112                              asect->rel_filepos,
3113                              SEEK_SET,
3114                              (size_t) (RELSZ *
3115                                        asect->reloc_count));
3116     reloc_cache = (arelent *)
3117       bfd_alloc(abfd, (size_t) (asect->reloc_count * sizeof(arelent)));
3118
3119     if (reloc_cache == NULL) {
3120       bfd_error = no_memory;
3121       return false;
3122     } {                         /* on error */
3123       arelent        *cache_ptr;
3124       RELOC   *src;
3125       for (cache_ptr = reloc_cache,
3126            src = native_relocs;
3127            cache_ptr < reloc_cache + asect->reloc_count;
3128            cache_ptr++,
3129            src++) {
3130         struct internal_reloc dst;
3131         asymbol        *ptr;
3132         bfd_swap_reloc_in(abfd, src, &dst);
3133
3134         dst.r_symndx += obj_symbol_slew(abfd);
3135         cache_ptr->sym_ptr_ptr = symbols + obj_convert(abfd)[dst.r_symndx];
3136 #ifdef A29K
3137         /* AMD has two relocation entries for the 'consth' instruction.
3138          * The first is R_IHIHALF (part 1), the second is R_IHCONST
3139          * (part 2).  The second entry's r_symndx does not contain
3140          * an index to a symbol but rather a value (apparently).
3141          * Also, see the ifdef below for saving the r_symndx value in addend.
3142          */
3143         if (dst.r_type == R_IHCONST)  {
3144                 ptr = NULL;
3145         } else
3146 #endif
3147         ptr = *(cache_ptr->sym_ptr_ptr);
3148         cache_ptr->address = dst.r_vaddr;
3149         /*
3150           The symbols definitions that we have read in have been
3151           relocated as if their sections started at 0. But the offsets
3152           refering to the symbols in the raw data have not been
3153           modified, so we have to have a negative addend to compensate.
3154
3155           Note that symbols which used to be common must be left alone */
3156
3157         if (ptr && ptr->the_bfd == abfd
3158             && ptr->section != (asection *) NULL
3159             && ((ptr->flags & BSF_OLD_COMMON)== 0))
3160             {
3161 #ifndef M88
3162               cache_ptr->addend = -(ptr->section->vma + ptr->value);
3163 #else
3164               cache_ptr->addend = 0;
3165 #endif
3166
3167             }
3168         else {
3169           cache_ptr->addend = 0;
3170         }
3171
3172         cache_ptr->address -= asect->vma;
3173
3174         cache_ptr->section = (asection *) NULL;
3175
3176 #ifdef A29K
3177         if (dst.r_type == R_IHCONST) {
3178           /* Add in the value which was stored in the symbol index */
3179           /* See above comment */
3180           cache_ptr->addend += dst.r_symndx;
3181           /* Throw away the bogus symbol pointer */
3182           cache_ptr->sym_ptr_ptr = 0;
3183         }
3184         cache_ptr->howto = howto_table + dst.r_type;
3185 #endif
3186 #if I386
3187         cache_ptr->howto = howto_table + dst.r_type;
3188 #endif
3189 #if I960
3190         cache_ptr->howto = howto_table + dst.r_type;
3191 #endif
3192 #if M68
3193         cache_ptr->howto = howto_table + dst.r_type - R_RELBYTE;
3194 #endif
3195 #if M88
3196         if (dst.r_type >= R_PCR16L && dst.r_type <= R_VRT32) {
3197           cache_ptr->howto = howto_table + dst.r_type - R_PCR16L;
3198           cache_ptr->addend += dst.r_offset << 16;
3199         }
3200         else {
3201           BFD_ASSERT(0);
3202         }
3203 #endif
3204       }
3205     }
3206
3207     asect->relocation = reloc_cache;
3208     return true;
3209   }
3210
3211
3212 /* This is stupid.  This function should be a boolean predicate */
3213 static unsigned int
3214 coff_canonicalize_reloc(abfd, section, relptr, symbols)
3215 bfd            *abfd;
3216 sec_ptr         section;
3217 arelent       **relptr;
3218 asymbol       **symbols;
3219   {
3220     arelent        *tblptr = section->relocation;
3221     unsigned int    count = 0;
3222     if (!(tblptr || coff_slurp_reloc_table(abfd, section, symbols)))
3223       return 0;
3224     tblptr = section->relocation;
3225     if (!tblptr)
3226       return 0;
3227
3228     for (; count++ < section->reloc_count;)
3229       *relptr++ = tblptr++;
3230
3231     *relptr = 0;
3232
3233     return section->reloc_count;
3234   }
3235
3236 #ifndef NO_COFF_SYMBOLS
3237
3238 /*
3239 provided a BFD, a section and an offset into the section, calculate and
3240 return the name of the source file and the line nearest to the wanted
3241 location.
3242 */
3243
3244 static          boolean
3245 DEFUN(coff_find_nearest_line,(abfd,
3246                               section,
3247                               ignore_symbols,
3248                               offset,
3249                               filename_ptr,
3250                               functionname_ptr,
3251                               line_ptr),
3252       bfd            *abfd AND
3253       asection       *section AND
3254       asymbol       **ignore_symbols AND
3255       bfd_vma         offset AND
3256       CONST char      **filename_ptr AND
3257       CONST char       **functionname_ptr AND
3258       unsigned int   *line_ptr)
3259 {
3260   static bfd     *cache_abfd;
3261   static asection *cache_section;
3262   static bfd_vma  cache_offset;
3263   static unsigned int cache_i;
3264   static alent   *cache_l;
3265
3266   unsigned int    i = 0;
3267   coff_data_type *cof = coff_data(abfd);
3268   /* Run through the raw syments if available */
3269   combined_entry_type *p;
3270   alent          *l;
3271   unsigned int    line_base = 0;
3272
3273
3274   *filename_ptr = 0;
3275   *functionname_ptr = 0;
3276   *line_ptr = 0;
3277
3278   /* Don't try and find line numbers in a non coff file */
3279   if (abfd->xvec->flavour != bfd_target_coff_flavour)
3280     return false;
3281
3282   if (cof == NULL)
3283     return false;
3284
3285   p = cof->raw_syments;
3286
3287   for (i = 0; i < cof->raw_syment_count; i++) {
3288     if (p->u.syment.n_sclass == C_FILE) {
3289       /* File name has been moved into symbol */
3290       *filename_ptr = (char *) p->u.syment._n._n_n._n_offset;
3291       break;
3292     }
3293     p += 1 +  p->u.syment.n_numaux;
3294   }
3295   /* Now wander though the raw linenumbers of the section */
3296   /*
3297     If this is the same BFD as we were previously called with and this is
3298     the same section, and the offset we want is further down then we can
3299     prime the lookup loop
3300     */
3301   if (abfd == cache_abfd &&
3302       section == cache_section &&
3303       offset >= cache_offset) {
3304     i = cache_i;
3305     l = cache_l;
3306   }
3307   else {
3308     i = 0;
3309     l = section->lineno;
3310   }
3311
3312   for (; i < section->lineno_count; i++) {
3313     if (l->line_number == 0) {
3314       /* Get the symbol this line number points at */
3315       coff_symbol_type *coff = (coff_symbol_type *) (l->u.sym);
3316       *functionname_ptr = coff->symbol.name;
3317       if (coff->native) {
3318         combined_entry_type  *s = coff->native;
3319         s = s + 1 + s->u.syment.n_numaux;
3320         /*
3321           S should now point to the .bf of the function
3322           */
3323         if (s->u.syment.n_numaux) {
3324           /*
3325             The linenumber is stored in the auxent
3326             */
3327           union internal_auxent   *a = &((s + 1)->u.auxent);
3328           line_base = a->x_sym.x_misc.x_lnsz.x_lnno;
3329         }
3330       }
3331     }
3332     else {
3333       if (l->u.offset > offset)
3334         break;
3335       *line_ptr = l->line_number + line_base + 1;
3336     }
3337     l++;
3338   }
3339
3340   cache_abfd = abfd;
3341   cache_section = section;
3342   cache_offset = offset;
3343   cache_i = i;
3344   cache_l = l;
3345
3346   return true;
3347 }
3348
3349 #ifdef GNU960
3350 file_ptr
3351 coff_sym_filepos(abfd)
3352 bfd *abfd;
3353   {
3354     return obj_sym_filepos(abfd);
3355   }
3356 #endif
3357
3358 #endif /* NO_COFF_SYMBOLS */
3359
3360
3361 static int
3362 DEFUN(coff_sizeof_headers,(abfd, reloc),
3363       bfd *abfd AND
3364       boolean reloc)
3365   {
3366     size_t size;
3367
3368     if (reloc == false) {
3369       size = FILHSZ + AOUTSZ;
3370     }
3371     else {
3372       size = FILHSZ;
3373     }
3374
3375     size +=  abfd->section_count * SCNHSZ;
3376     return size;
3377   }
3378
3379
3380 #define coff_core_file_failing_command  _bfd_dummy_core_file_failing_command
3381 #define coff_core_file_failing_signal   _bfd_dummy_core_file_failing_signal
3382 #define coff_core_file_matches_executable_p     _bfd_dummy_core_file_matches_executable_p
3383 #define coff_slurp_armap                bfd_slurp_coff_armap
3384 #define coff_slurp_extended_name_table  _bfd_slurp_extended_name_table
3385 #define coff_truncate_arname            bfd_dont_truncate_arname
3386 #define coff_openr_next_archived_file   bfd_generic_openr_next_archived_file
3387 #define coff_generic_stat_arch_elt      bfd_generic_stat_arch_elt
3388 #define coff_get_section_contents       bfd_generic_get_section_contents
3389 #define coff_close_and_cleanup          bfd_generic_close_and_cleanup
3390
3391 #define coff_bfd_debug_info_start               bfd_void
3392 #define coff_bfd_debug_info_end         bfd_void
3393 #define coff_bfd_debug_info_accumulate  (PROTO(void,(*),(bfd*, struct sec *))) bfd_void