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.
5 This file is part of BFD, the Binary File Descriptor library.
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.
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.
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. */
22 @section coff backends
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.
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}.
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}.
44 @subsection Porting To A New Version of Coff
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
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.
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.
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
69 @subsection How The Coff Backend Works
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}.
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.
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.
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,
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.
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"}).
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.
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
139 Any linenumbers are read from the coff file too, and attached to the
140 symbols which own the functions the linenumbers belong to.
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
149 When the symbols have come from a coff file then all the debugging
150 information is preserved.
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
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
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
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}
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.
192 The hidden information for an asymbol is:
196 $ typedef struct coff_ptr_struct
199 Remembers the offset from the first symbol in the file for this
200 symbol. Generated by @code{coff_renumber_symbols}.
202 $ unsigned int offset;
204 Should the tag field of this symbol be renumbered.
205 Created by @code{coff_pointerize_aux}.
209 Should the endidx field of this symbol be renumbered.
210 Created by @code{coff_pointerize_aux}.
214 The container for the symbol structure as read and translated from the file.
217 $ union internal_auxent auxent;
218 $ struct internal_syment syment;
220 $ } combined_entry_type;
225 Each canonical asymbol really looks like this:
229 $ typedef struct coff_symbol_struct
232 The actual symbol which the rest of BFD works with
236 A pointer to the hidden information for this symbol
238 $ combined_entry_type *native;
240 A pointer to the linenumber information for this symbol
242 $ struct lineno_cache_entry *lineno;
243 $ } coff_symbol_type;
250 /* Most of this hacked by Steve Chamberlain, steve@cygnus.com */
253 #define PUTWORD bfd_h_put_32
254 #define PUTHALF bfd_h_put_16
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)
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)
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)
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)
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)
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)
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)
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)
282 #ifndef GET_SCN_SCNLEN
283 #define GET_SCN_SCNLEN(abfd, ext) bfd_h_get_32(abfd, (bfd_byte *) ext->x_scn.x_scnlen)
285 #ifndef GET_SCN_NRELOC
286 #define GET_SCN_NRELOC(abfd, ext) bfd_h_get_16(abfd, (bfd_byte *)ext->x_scn.x_nreloc)
288 #ifndef GET_SCN_NLINNO
289 #define GET_SCN_NLINNO(abfd, ext) bfd_h_get_16(abfd, (bfd_byte *)ext->x_scn.x_nlinno)
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)
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)
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)
303 /* void warning(); */
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().
312 DEFUN(sec_to_styp_flags
, (sec_name
, sec_flags
),
313 CONST
char * sec_name AND
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
);
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
;
333 styp_flags
= STYP_TEXT
;
334 #endif /* STYP_LIT */
335 else if (sec_flags
& SEC_LOAD
) styp_flags
= STYP_TEXT
;
337 if (styp_flags
== 0) styp_flags
= STYP_BSS
;
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().
349 DEFUN(styp_to_sec_flags
, (styp_flags
),
352 flagword sec_flags
=0;
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
;
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 */
367 #define get_index(symbol) ((int) (symbol)->value)
368 #define set_index(symbol, idx) ((symbol)->value = (idx))
370 /* **********************************************************************
371 Here are all the routines for swapping the structures seen in the
372 outside world into the internal forms.
377 DEFUN(bfd_swap_reloc_in
,(abfd
, reloc_src
, reloc_dst
),
380 struct internal_reloc
*reloc_dst
)
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 reloc_dst
->r_type
= bfd_h_get_16(abfd
, (bfd_byte
*) reloc_src
->r_type
);
386 reloc_dst
->r_offset
= bfd_h_get_16(abfd
, (bfd_byte
*) reloc_src
->r_offset
);
392 DEFUN(coff_swap_reloc_out
,(abfd
, src
, dst
),
397 struct internal_reloc
*reloc_src
= (struct internal_reloc
*)src
;
398 struct external_reloc
*reloc_dst
= (struct external_reloc
*)dst
;
399 bfd_h_put_32(abfd
, reloc_src
->r_vaddr
, (bfd_byte
*) reloc_dst
->r_vaddr
);
400 bfd_h_put_32(abfd
, reloc_src
->r_symndx
, (bfd_byte
*) reloc_dst
->r_symndx
);
401 bfd_h_put_16(abfd
, reloc_src
->r_type
, (bfd_byte
*) reloc_dst
->r_type
);
403 bfd_h_put_16(abfd
, reloc_src
->r_offset
, (bfd_byte
*) reloc_dst
->r_offset
);
405 return sizeof(struct external_reloc
);
409 DEFUN(bfd_swap_filehdr_in
,(abfd
, filehdr_src
, filehdr_dst
),
411 FILHDR
*filehdr_src AND
412 struct internal_filehdr
*filehdr_dst
)
414 filehdr_dst
->f_magic
= bfd_h_get_16(abfd
, (bfd_byte
*) filehdr_src
->f_magic
);
415 filehdr_dst
->f_nscns
= bfd_h_get_16(abfd
, (bfd_byte
*)filehdr_src
-> f_nscns
);
416 filehdr_dst
->f_timdat
= bfd_h_get_32(abfd
, (bfd_byte
*)filehdr_src
-> f_timdat
);
417 filehdr_dst
->f_symptr
= bfd_h_get_32(abfd
, (bfd_byte
*)filehdr_src
-> f_symptr
);
418 filehdr_dst
->f_nsyms
= bfd_h_get_32(abfd
, (bfd_byte
*)filehdr_src
-> f_nsyms
);
419 filehdr_dst
->f_opthdr
= bfd_h_get_16(abfd
, (bfd_byte
*)filehdr_src
-> f_opthdr
);
420 filehdr_dst
->f_flags
= bfd_h_get_16(abfd
, (bfd_byte
*)filehdr_src
-> f_flags
);
424 DEFUN(coff_swap_filehdr_out
,(abfd
, in
, out
),
429 struct internal_filehdr
*filehdr_in
= (struct internal_filehdr
*)in
;
430 FILHDR
*filehdr_out
= (FILHDR
*)out
;
431 bfd_h_put_16(abfd
, filehdr_in
->f_magic
, (bfd_byte
*) filehdr_out
->f_magic
);
432 bfd_h_put_16(abfd
, filehdr_in
->f_nscns
, (bfd_byte
*) filehdr_out
->f_nscns
);
433 bfd_h_put_32(abfd
, filehdr_in
->f_timdat
, (bfd_byte
*) filehdr_out
->f_timdat
);
434 bfd_h_put_32(abfd
, filehdr_in
->f_symptr
, (bfd_byte
*) filehdr_out
->f_symptr
);
435 bfd_h_put_32(abfd
, filehdr_in
->f_nsyms
, (bfd_byte
*) filehdr_out
->f_nsyms
);
436 bfd_h_put_16(abfd
, filehdr_in
->f_opthdr
, (bfd_byte
*) filehdr_out
->f_opthdr
);
437 bfd_h_put_16(abfd
, filehdr_in
->f_flags
, (bfd_byte
*) filehdr_out
->f_flags
);
438 return sizeof(FILHDR
);
442 #ifndef NO_COFF_SYMBOLS
445 DEFUN(coff_swap_sym_in
,(abfd
, ext1
, in1
),
450 SYMENT
*ext
= (SYMENT
*)ext1
;
451 struct internal_syment
*in
= (struct internal_syment
*)in1
;
453 if( ext
->e
.e_name
[0] == 0) {
454 in
->_n
._n_n
._n_zeroes
= 0;
455 in
->_n
._n_n
._n_offset
= bfd_h_get_32(abfd
, (bfd_byte
*) ext
->e
.e
.e_offset
);
458 #if SYMNMLEN != E_SYMNMLEN
459 -> Error
, we need to cope with truncating
or extending SYMNMLEN
!;
461 memcpy(in
->_n
._n_name
, ext
->e
.e_name
, SYMNMLEN
);
464 in
->n_value
= bfd_h_get_32(abfd
, (bfd_byte
*) ext
->e_value
);
465 in
->n_scnum
= bfd_h_get_16(abfd
, (bfd_byte
*) ext
->e_scnum
);
466 if (sizeof(ext
->e_type
) == 2){
467 in
->n_type
= bfd_h_get_16(abfd
, (bfd_byte
*) ext
->e_type
);
470 in
->n_type
= bfd_h_get_32(abfd
, (bfd_byte
*) ext
->e_type
);
472 in
->n_sclass
= bfd_h_get_8(abfd
, ext
->e_sclass
);
473 in
->n_numaux
= bfd_h_get_8(abfd
, ext
->e_numaux
);
477 DEFUN(coff_swap_sym_out
,(abfd
, inp
, extp
),
482 struct internal_syment
*in
= (struct internal_syment
*)inp
;
483 SYMENT
*ext
=(SYMENT
*)extp
;
484 if(in
->_n
._n_name
[0] == 0) {
485 bfd_h_put_32(abfd
, 0, (bfd_byte
*) ext
->e
.e
.e_zeroes
);
486 bfd_h_put_32(abfd
, in
->_n
._n_n
._n_offset
, (bfd_byte
*) ext
->e
.e
.e_offset
);
489 #if SYMNMLEN != E_SYMNMLEN
490 -> Error
, we need to cope with truncating
or extending SYMNMLEN
!;
492 memcpy(ext
->e
.e_name
, in
->_n
._n_name
, SYMNMLEN
);
495 bfd_h_put_32(abfd
, in
->n_value
, (bfd_byte
*) ext
->e_value
);
496 bfd_h_put_16(abfd
, in
->n_scnum
, (bfd_byte
*) ext
->e_scnum
);
497 if (sizeof(ext
->e_type
) == 2)
499 bfd_h_put_16(abfd
, in
->n_type
, (bfd_byte
*) ext
->e_type
);
503 bfd_h_put_32(abfd
, in
->n_type
, (bfd_byte
*) ext
->e_type
);
505 bfd_h_put_8(abfd
, in
->n_sclass
, ext
->e_sclass
);
506 bfd_h_put_8(abfd
, in
->n_numaux
, ext
->e_numaux
);
507 return sizeof(SYMENT
);
511 DEFUN(coff_swap_aux_in
,(abfd
, ext1
, type
, class, in1
),
518 AUXENT
*ext
= (AUXENT
*)ext1
;
519 union internal_auxent
*in
= (union internal_auxent
*)in1
;
522 if (ext
->x_file
.x_fname
[0] == 0) {
523 in
->x_file
.x_n
.x_zeroes
= 0;
524 in
->x_file
.x_n
.x_offset
= bfd_h_get_32(abfd
, (bfd_byte
*) ext
->x_file
.x_n
.x_offset
);
526 #if FILNMLEN != E_FILNMLEN
527 -> Error
, we need to cope with truncating
or extending FILNMLEN
!;
529 memcpy (in
->x_file
.x_fname
, ext
->x_file
.x_fname
, FILNMLEN
);
539 if (type
== T_NULL
) {
540 in
->x_scn
.x_scnlen
= GET_SCN_SCNLEN(abfd
, ext
);
541 in
->x_scn
.x_nreloc
= GET_SCN_NRELOC(abfd
, ext
);
542 in
->x_scn
.x_nlinno
= GET_SCN_NLINNO(abfd
, ext
);
546 in
->x_sym
.x_tagndx
.l
= bfd_h_get_32(abfd
, (bfd_byte
*) ext
->x_sym
.x_tagndx
);
548 in
->x_sym
.x_tvndx
= bfd_h_get_16(abfd
, (bfd_byte
*) ext
->x_sym
.x_tvndx
);
551 if (ISARY(type
) || class == C_BLOCK
) {
552 #if DIMNUM != E_DIMNUM
553 -> Error
, we need to cope with truncating
or extending DIMNUM
!;
555 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]);
556 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]);
557 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]);
558 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]);
561 in
->x_sym
.x_fcnary
.x_fcn
.x_lnnoptr
= GET_FCN_LNNOPTR(abfd
, ext
);
562 in
->x_sym
.x_fcnary
.x_fcn
.x_endndx
.l
= GET_FCN_ENDNDX(abfd
, ext
);
565 in
->x_sym
.x_misc
.x_fsize
= bfd_h_get_32(abfd
, (bfd_byte
*) ext
->x_sym
.x_misc
.x_fsize
);
568 in
->x_sym
.x_misc
.x_lnsz
.x_lnno
= GET_LNSZ_LNNO(abfd
, ext
);
569 in
->x_sym
.x_misc
.x_lnsz
.x_size
= GET_LNSZ_SIZE(abfd
, ext
);
575 DEFUN(coff_swap_aux_out
,(abfd
, inp
, type
, class, extp
),
582 union internal_auxent
*in
= (union internal_auxent
*)inp
;
583 AUXENT
*ext
= (AUXENT
*)extp
;
586 if (in
->x_file
.x_fname
[0] == 0) {
587 PUTWORD(abfd
, 0, (bfd_byte
*) ext
->x_file
.x_n
.x_zeroes
);
589 in
->x_file
.x_n
.x_offset
,
590 (bfd_byte
*) ext
->x_file
.x_n
.x_offset
);
593 #if FILNMLEN != E_FILNMLEN
594 -> Error
, we need to cope with truncating
or extending FILNMLEN
!;
596 memcpy (ext
->x_file
.x_fname
, in
->x_file
.x_fname
, FILNMLEN
);
605 if (type
== T_NULL
) {
607 PUT_SCN_SCNLEN(abfd
, in
->x_scn
.x_scnlen
, ext
);
608 PUT_SCN_NRELOC(abfd
, in
->x_scn
.x_nreloc
, ext
);
609 PUT_SCN_NLINNO(abfd
, in
->x_scn
.x_nlinno
, ext
);
613 PUTWORD(abfd
, in
->x_sym
.x_tagndx
.l
, (bfd_byte
*) ext
->x_sym
.x_tagndx
);
615 PUTWORD(abfd
, in
->x_sym
.x_tvndx
, (bfd_byte
*) ext
->x_sym
.x_tvndx
);
619 PUTWORD(abfd
, in
->x_sym
.x_misc
.x_fsize
, (bfd_byte
*) ext
->x_sym
.x_misc
.x_fsize
);
620 PUT_FCN_LNNOPTR(abfd
, in
->x_sym
.x_fcnary
.x_fcn
.x_lnnoptr
, ext
);
621 PUT_FCN_ENDNDX(abfd
, in
->x_sym
.x_fcnary
.x_fcn
.x_endndx
.l
, ext
);
625 if (ISARY(type
) || class == C_BLOCK
) {
626 #if DIMNUM != E_DIMNUM
627 -> Error
, we need to cope with truncating
or extending DIMNUM
!;
629 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]);
630 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]);
631 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]);
632 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]);
635 PUT_LNSZ_LNNO(abfd
, in
->x_sym
.x_misc
.x_lnsz
.x_lnno
, ext
);
636 PUT_LNSZ_SIZE(abfd
, in
->x_sym
.x_misc
.x_lnsz
.x_size
, ext
);
638 PUT_FCN_LNNOPTR(abfd
, in
->x_sym
.x_fcnary
.x_fcn
.x_lnnoptr
, ext
);
639 PUT_FCN_ENDNDX(abfd
, in
->x_sym
.x_fcnary
.x_fcn
.x_endndx
.l
, ext
);
644 return sizeof(AUXENT
);
647 #endif /* NO_COFF_SYMBOLS */
649 #ifndef NO_COFF_LINENOS
652 DEFUN(coff_swap_lineno_in
,(abfd
, ext1
, in1
),
657 LINENO
*ext
= (LINENO
*)ext1
;
658 struct internal_lineno
*in
= (struct internal_lineno
*)in1
;
660 in
->l_addr
.l_symndx
= bfd_h_get_32(abfd
, (bfd_byte
*) ext
->l_addr
.l_symndx
);
662 in
->l_lnno
= bfd_h_get_32(abfd
, (bfd_byte
*) ext
->l_lnno
);
664 in
->l_lnno
= bfd_h_get_16(abfd
, (bfd_byte
*) ext
->l_lnno
);
669 DEFUN(coff_swap_lineno_out
,(abfd
, inp
, outp
),
674 struct internal_lineno
*in
= (struct internal_lineno
*)inp
;
675 struct external_lineno
*ext
= (struct external_lineno
*)outp
;
676 PUTWORD(abfd
, in
->l_addr
.l_symndx
, (bfd_byte
*) ext
->l_addr
.l_symndx
);
678 PUTWORD(abfd
, in
->l_lnno
, (bfd_byte
*) ext
->l_lnno
);
680 PUTHALF(abfd
, in
->l_lnno
, (bfd_byte
*) ext
->l_lnno
);
682 return sizeof(struct external_lineno
);
685 #endif /* NO_COFF_LINENOS */
689 DEFUN(bfd_swap_aouthdr_in
,(abfd
, aouthdr_ext1
, aouthdr_int1
),
694 AOUTHDR
*aouthdr_ext
= (AOUTHDR
*) aouthdr_ext1
;
695 struct internal_aouthdr
*aouthdr_int
= (struct internal_aouthdr
*)aouthdr_int1
;
697 aouthdr_int
->magic
= bfd_h_get_16(abfd
, (bfd_byte
*) aouthdr_ext
->magic
);
698 aouthdr_int
->vstamp
= bfd_h_get_16(abfd
, (bfd_byte
*) aouthdr_ext
->vstamp
);
699 aouthdr_int
->tsize
= bfd_h_get_32(abfd
, (bfd_byte
*) aouthdr_ext
->tsize
);
700 aouthdr_int
->dsize
= bfd_h_get_32(abfd
, (bfd_byte
*) aouthdr_ext
->dsize
);
701 aouthdr_int
->bsize
= bfd_h_get_32(abfd
, (bfd_byte
*) aouthdr_ext
->bsize
);
702 aouthdr_int
->entry
= bfd_h_get_32(abfd
, (bfd_byte
*) aouthdr_ext
->entry
);
703 aouthdr_int
->text_start
= bfd_h_get_32(abfd
, (bfd_byte
*) aouthdr_ext
->text_start
);
704 aouthdr_int
->data_start
= bfd_h_get_32(abfd
, (bfd_byte
*) aouthdr_ext
->data_start
);
706 aouthdr_int
->tagentries
= bfd_h_get_32(abfd
, (bfd_byte
*) aouthdr_ext
->tagentries
);
711 DEFUN(coff_swap_aouthdr_out
,(abfd
, in
, out
),
716 struct internal_aouthdr
*aouthdr_in
= (struct internal_aouthdr
*)in
;
717 AOUTHDR
*aouthdr_out
= (AOUTHDR
*)out
;
718 bfd_h_put_16(abfd
, aouthdr_in
->magic
, (bfd_byte
*) aouthdr_out
->magic
);
719 bfd_h_put_16(abfd
, aouthdr_in
->vstamp
, (bfd_byte
*) aouthdr_out
->vstamp
);
720 bfd_h_put_32(abfd
, aouthdr_in
->tsize
, (bfd_byte
*) aouthdr_out
->tsize
);
721 bfd_h_put_32(abfd
, aouthdr_in
->dsize
, (bfd_byte
*) aouthdr_out
->dsize
);
722 bfd_h_put_32(abfd
, aouthdr_in
->bsize
, (bfd_byte
*) aouthdr_out
->bsize
);
723 bfd_h_put_32(abfd
, aouthdr_in
->entry
, (bfd_byte
*) aouthdr_out
->entry
);
724 bfd_h_put_32(abfd
, aouthdr_in
->text_start
,
725 (bfd_byte
*) aouthdr_out
->text_start
);
726 bfd_h_put_32(abfd
, aouthdr_in
->data_start
, (bfd_byte
*) aouthdr_out
->data_start
);
728 bfd_h_put_32(abfd
, aouthdr_in
->tagentries
, (bfd_byte
*) aouthdr_out
->tagentries
);
730 return sizeof(AOUTHDR
);
734 DEFUN(coff_swap_scnhdr_in
,(abfd
, scnhdr_ext
, scnhdr_int
),
736 SCNHDR
*scnhdr_ext AND
737 struct internal_scnhdr
*scnhdr_int
)
739 memcpy(scnhdr_int
->s_name
, scnhdr_ext
->s_name
, sizeof(scnhdr_int
->s_name
));
740 scnhdr_int
->s_vaddr
= bfd_h_get_32(abfd
, (bfd_byte
*) scnhdr_ext
->s_vaddr
);
741 scnhdr_int
->s_paddr
= bfd_h_get_32(abfd
, (bfd_byte
*) scnhdr_ext
->s_paddr
);
742 scnhdr_int
->s_size
= bfd_h_get_32(abfd
, (bfd_byte
*) scnhdr_ext
->s_size
);
743 scnhdr_int
->s_scnptr
= bfd_h_get_32(abfd
, (bfd_byte
*) scnhdr_ext
->s_scnptr
);
744 scnhdr_int
->s_relptr
= bfd_h_get_32(abfd
, (bfd_byte
*) scnhdr_ext
->s_relptr
);
745 scnhdr_int
->s_lnnoptr
= bfd_h_get_32(abfd
, (bfd_byte
*) scnhdr_ext
->s_lnnoptr
);
746 scnhdr_int
->s_flags
= bfd_h_get_32(abfd
, (bfd_byte
*) scnhdr_ext
->s_flags
);
748 scnhdr_int
->s_nreloc
= bfd_h_get_32(abfd
, (bfd_byte
*) scnhdr_ext
->s_nreloc
);
749 scnhdr_int
->s_nlnno
= bfd_h_get_32(abfd
, (bfd_byte
*) scnhdr_ext
->s_nlnno
);
751 scnhdr_int
->s_nreloc
= bfd_h_get_16(abfd
, (bfd_byte
*) scnhdr_ext
->s_nreloc
);
752 scnhdr_int
->s_nlnno
= bfd_h_get_16(abfd
, (bfd_byte
*) scnhdr_ext
->s_nlnno
);
755 scnhdr_int
->s_align
= bfd_h_get_32(abfd
, (bfd_byte
*) scnhdr_ext
->s_align
);
760 DEFUN(coff_swap_scnhdr_out
,(abfd
, in
, out
),
765 struct internal_scnhdr
*scnhdr_int
= (struct internal_scnhdr
*)in
;
766 SCNHDR
*scnhdr_ext
= (SCNHDR
*)out
;
767 memcpy(scnhdr_ext
->s_name
, scnhdr_int
->s_name
, sizeof(scnhdr_int
->s_name
));
768 PUTWORD(abfd
, scnhdr_int
->s_vaddr
, (bfd_byte
*) scnhdr_ext
->s_vaddr
);
769 PUTWORD(abfd
, scnhdr_int
->s_paddr
, (bfd_byte
*) scnhdr_ext
->s_paddr
);
770 PUTWORD(abfd
, scnhdr_int
->s_size
, (bfd_byte
*) scnhdr_ext
->s_size
);
771 PUTWORD(abfd
, scnhdr_int
->s_scnptr
, (bfd_byte
*) scnhdr_ext
->s_scnptr
);
772 PUTWORD(abfd
, scnhdr_int
->s_relptr
, (bfd_byte
*) scnhdr_ext
->s_relptr
);
773 PUTWORD(abfd
, scnhdr_int
->s_lnnoptr
, (bfd_byte
*) scnhdr_ext
->s_lnnoptr
);
774 PUTWORD(abfd
, scnhdr_int
->s_flags
, (bfd_byte
*) scnhdr_ext
->s_flags
);
776 PUTWORD(abfd
, scnhdr_int
->s_nlnno
, (bfd_byte
*) scnhdr_ext
->s_nlnno
);
777 PUTWORD(abfd
, scnhdr_int
->s_nreloc
, (bfd_byte
*) scnhdr_ext
->s_nreloc
);
779 PUTHALF(abfd
, scnhdr_int
->s_nlnno
, (bfd_byte
*) scnhdr_ext
->s_nlnno
);
780 PUTHALF(abfd
, scnhdr_int
->s_nreloc
, (bfd_byte
*) scnhdr_ext
->s_nreloc
);
784 PUTWORD(abfd
, scnhdr_int
->s_align
, (bfd_byte
*) scnhdr_ext
->s_align
);
786 return sizeof(SCNHDR
);
791 initialize a section structure with information peculiar to this
792 particular implementation of coff
796 DEFUN(coff_new_section_hook
,(abfd_ignore
, section_ignore
),
798 asection
*section_ignore
)
800 section_ignore
->alignment_power
= abfd_ignore
->xvec
->align_power_min
;
804 /* Take a section header read from a coff file (in HOST byte order),
805 and make a BFD "section" out of it. */
807 DEFUN(make_a_section_from_file
,(abfd
, hdr
),
809 struct internal_scnhdr
*hdr
)
811 asection
*return_section
;
814 /* Assorted wastage to null-terminate the name, thanks AT&T! */
815 char *name
= bfd_alloc(abfd
, sizeof (hdr
->s_name
)+1);
817 bfd_error
= no_memory
;
820 strncpy(name
, (char *) &hdr
->s_name
[0], sizeof (hdr
->s_name
));
821 name
[sizeof (hdr
->s_name
)] = 0;
823 return_section
= bfd_make_section(abfd
, name
);
826 /* s_paddr is presumed to be = to s_vaddr */
827 #define assign(to, from) return_section->to = hdr->from
828 assign(vma
, s_vaddr
);
829 /* assign (vma, s_vaddr); */
830 assign(size
, s_size
);
831 assign(filepos
, s_scnptr
);
832 assign(rel_filepos
, s_relptr
);
833 assign(reloc_count
, s_nreloc
);
836 /* FIXME, use a temp var rather than alignment_power */
837 assign(alignment_power
, s_align
);
840 for (i
= 0; i
< 32; i
++) {
841 if ((1 << i
) >= (int) (return_section
->alignment_power
)) {
842 return_section
->alignment_power
= i
;
849 assign(line_filepos
, s_lnnoptr
);
851 return_section->linesize = hdr->s_nlnno * sizeof (struct lineno);
854 return_section
->lineno_count
= hdr
->s_nlnno
;
855 return_section
->userdata
= NULL
;
856 return_section
->next
= (asection
*) NULL
;
857 return_section
->flags
= styp_to_sec_flags(hdr
->s_flags
);
860 if (hdr
->s_nreloc
!= 0)
861 return_section
->flags
|= SEC_RELOC
;
862 /* FIXME: should this check 'hdr->s_size > 0' */
863 if (hdr
->s_scnptr
!= 0)
864 return_section
->flags
|= SEC_HAS_CONTENTS
;
868 DEFUN(coff_mkobject
,(abfd
),
871 set_tdata (abfd
, bfd_zalloc (abfd
,sizeof(coff_data_type
)));
872 if (coff_data(abfd
) == 0) {
873 bfd_error
= no_memory
;
876 coff_data(abfd
)->relocbase
= 0;
882 DEFUN(coff_real_object_p
,(abfd
, nscns
, internal_f
, internal_a
),
885 struct internal_filehdr
*internal_f AND
886 struct internal_aouthdr
*internal_a
)
888 coff_data_type
*coff
;
889 enum bfd_architecture arch
;
891 size_t readsize
; /* length of file_info */
892 SCNHDR
*external_sections
;
894 /* Build a play area */
895 if (coff_mkobject(abfd
) != true)
897 coff
= coff_data(abfd
);
900 external_sections
= (SCNHDR
*)bfd_alloc(abfd
, readsize
= (nscns
* SCNHSZ
));
902 if (bfd_read((PTR
)external_sections
, 1, readsize
, abfd
) != readsize
) {
907 /* Now copy data as required; construct all asections etc */
908 coff
->symbol_index_slew
= 0;
910 coff
->raw_syment_count
= 0;
911 coff
->raw_linenos
= 0;
912 coff
->raw_syments
= 0;
913 coff
->sym_filepos
=0;
914 coff
->flags
= internal_f
->f_flags
;
917 for (i
= 0; i
< nscns
; i
++) {
918 struct internal_scnhdr tmp
;
919 coff_swap_scnhdr_in(abfd
, external_sections
+ i
, &tmp
);
920 make_a_section_from_file(abfd
,&tmp
);
923 /* Determine the machine architecture and type. */
925 switch (internal_f
->f_magic
) {
928 arch
= bfd_arch_i386
;
933 #ifdef A29K_MAGIC_BIG
935 case A29K_MAGIC_LITTLE
:
936 arch
= bfd_arch_a29k
;
945 arch
= bfd_arch_mips
;
953 arch
= bfd_arch_m68k
;
961 arch
= bfd_arch_m88k
;
969 arch
= bfd_arch_i960
;
970 switch (F_I960TYPE
& internal_f
->f_flags
)
974 machine
= bfd_mach_i960_core
;
977 machine
= bfd_mach_i960_kb_sb
;
980 machine
= bfd_mach_i960_mc
;
983 machine
= bfd_mach_i960_xa
;
986 machine
= bfd_mach_i960_ca
;
989 machine
= bfd_mach_i960_ka_sa
;
997 default: /* Unreadable input file type */
998 arch
= bfd_arch_obscure
;
1002 bfd_default_set_arch_mach(abfd
, arch
, machine
);
1003 if (!(internal_f
->f_flags
& F_RELFLG
))
1004 abfd
->flags
|= HAS_RELOC
;
1005 if ((internal_f
->f_flags
& F_EXEC
))
1006 abfd
->flags
|= EXEC_P
;
1007 if (!(internal_f
->f_flags
& F_LNNO
))
1008 abfd
->flags
|= HAS_LINENO
;
1009 if (!(internal_f
->f_flags
& F_LSYMS
))
1010 abfd
->flags
|= HAS_LOCALS
;
1013 bfd_get_symcount(abfd
) = internal_f
->f_nsyms
;
1014 if (internal_f
->f_nsyms
)
1015 abfd
->flags
|= HAS_SYMS
;
1017 coff
->sym_filepos
= internal_f
->f_symptr
;
1019 /* These members communicate important constants about the symbol table
1020 to GDB's symbol-reading code. These `constants' unfortunately vary
1021 from coff implementation to implementation... */
1022 #ifndef NO_COFF_SYMBOLS
1023 coff
->local_n_btmask
= N_BTMASK
;
1024 coff
->local_n_btshft
= N_BTSHFT
;
1025 coff
->local_n_tmask
= N_TMASK
;
1026 coff
->local_n_tshift
= N_TSHIFT
;
1027 coff
->local_symesz
= SYMESZ
;
1028 coff
->local_auxesz
= AUXESZ
;
1029 coff
->local_linesz
= LINESZ
;
1032 coff
->symbols
= (coff_symbol_type
*) NULL
;
1033 bfd_get_start_address(abfd
) = internal_f
->f_opthdr
? internal_a
->entry
: 0;
1037 bfd_release(abfd
, coff
);
1038 return (bfd_target
*)NULL
;
1042 DEFUN(coff_object_p
,(abfd
),
1048 struct internal_filehdr internal_f
;
1049 struct internal_aouthdr internal_a
;
1051 bfd_error
= system_call_error
;
1053 /* figure out how much to read */
1054 if (bfd_read((PTR
) &filehdr
, 1, FILHSZ
, abfd
) != FILHSZ
)
1057 bfd_swap_filehdr_in(abfd
, &filehdr
, &internal_f
);
1059 if (BADMAG(internal_f
)) {
1060 bfd_error
= wrong_format
;
1063 nscns
=internal_f
.f_nscns
;
1065 if (internal_f
.f_opthdr
) {
1066 if (bfd_read((PTR
) &opthdr
, 1,AOUTSZ
, abfd
) != AOUTSZ
) {
1069 bfd_swap_aouthdr_in(abfd
, (char *)&opthdr
, (char *)&internal_a
);
1072 /* Seek past the opt hdr stuff */
1073 bfd_seek(abfd
, internal_f
.f_opthdr
+ FILHSZ
, SEEK_SET
);
1075 /* if the optional header is NULL or not the correct size then
1076 quit; the only difference I can see between m88k dgux headers (MC88DMAGIC)
1077 and Intel 960 readwrite headers (I960WRMAGIC) is that the
1078 optional header is of a different size.
1080 But the mips keeps extra stuff in it's opthdr, so dont check
1084 #if defined(M88) || defined(I960)
1085 if (internal_f
.f_opthdr
!= 0 && AOUTSZ
!= internal_f
.f_opthdr
)
1086 return (bfd_target
*)NULL
;
1089 return coff_real_object_p(abfd
, nscns
, &internal_f
, &internal_a
);
1094 #ifndef NO_COFF_LINENOS
1097 DEFUN(coff_count_linenumbers
,(abfd
),
1100 unsigned int limit
= bfd_get_symcount(abfd
);
1104 asection
*s
= abfd
->sections
->output_section
;
1106 BFD_ASSERT(s
->lineno_count
== 0);
1112 for (p
= abfd
->outsymbols
, i
= 0; i
< limit
; i
++, p
++) {
1113 asymbol
*q_maybe
= *p
;
1114 if (q_maybe
->the_bfd
->xvec
->flavour
== bfd_target_coff_flavour
) {
1115 coff_symbol_type
*q
= coffsymbol(q_maybe
);
1118 This symbol has a linenumber, increment the owning
1119 section's linenumber count
1121 alent
*l
= q
->lineno
;
1122 q
->symbol
.section
->output_section
->lineno_count
++;
1124 while (l
->line_number
) {
1125 q
->symbol
.section
->output_section
->lineno_count
++;
1133 #endif /* NO_COFF_LINENOS */
1135 #ifndef NO_COFF_SYMBOLS
1138 Takes a bfd and a symbol, returns a pointer to the coff specific area
1139 of the symbol if there is one.
1141 static coff_symbol_type
*
1142 DEFUN(coff_symbol_from
,(ignore_abfd
, symbol
),
1143 bfd
*ignore_abfd AND
1146 if (symbol
->the_bfd
->xvec
->flavour
!= bfd_target_coff_flavour
)
1147 return (coff_symbol_type
*)NULL
;
1149 if (symbol
->the_bfd
->tdata
== (PTR
)NULL
)
1150 return (coff_symbol_type
*)NULL
;
1152 return (coff_symbol_type
*) symbol
;
1158 DEFUN(fixup_symbol_value
,(coff_symbol_ptr
, syment
),
1159 coff_symbol_type
*coff_symbol_ptr AND
1160 struct internal_syment
*syment
)
1163 /* Normalize the symbol flags */
1164 if (coff_symbol_ptr
->symbol
.flags
& BSF_FORT_COMM
) {
1165 /* a common symbol is undefined with a value */
1166 syment
->n_scnum
= N_UNDEF
;
1167 syment
->n_value
= coff_symbol_ptr
->symbol
.value
;
1169 else if (coff_symbol_ptr
->symbol
.flags
& BSF_DEBUGGING
) {
1170 syment
->n_value
= coff_symbol_ptr
->symbol
.value
;
1172 else if (coff_symbol_ptr
->symbol
.flags
& BSF_UNDEFINED
) {
1173 syment
->n_scnum
= N_UNDEF
;
1174 syment
->n_value
= 0;
1176 else if (coff_symbol_ptr
->symbol
.flags
& BSF_ABSOLUTE
) {
1177 syment
->n_scnum
= N_ABS
;
1178 syment
->n_value
= coff_symbol_ptr
->symbol
.value
;
1181 if (coff_symbol_ptr
->symbol
.section
) {
1183 coff_symbol_ptr
->symbol
.section
->output_section
->index
+1;
1186 coff_symbol_ptr
->symbol
.value
+
1187 coff_symbol_ptr
->symbol
.section
->output_offset
+
1188 coff_symbol_ptr
->symbol
.section
->output_section
->vma
;
1191 /* This can happen, but I don't know why yet (steve@cygnus.com) */
1192 syment
->n_scnum
= N_ABS
;
1193 syment
->n_value
= coff_symbol_ptr
->symbol
.value
;
1198 /* run through all the symbols in the symbol table and work out what
1199 their indexes into the symbol table will be when output
1201 Coff requires that each C_FILE symbol points to the next one in the
1202 chain, and that the last one points to the first external symbol. We
1207 DEFUN(coff_renumber_symbols
,(bfd_ptr
),
1210 unsigned int symbol_count
= bfd_get_symcount(bfd_ptr
);
1211 asymbol
**symbol_ptr_ptr
= bfd_ptr
->outsymbols
;
1212 unsigned int native_index
= 0;
1213 struct internal_syment
*last_file
= (struct internal_syment
*)NULL
;
1214 unsigned int symbol_index
;
1215 for (symbol_index
= 0; symbol_index
< symbol_count
; symbol_index
++)
1217 coff_symbol_type
*coff_symbol_ptr
= coff_symbol_from(bfd_ptr
, symbol_ptr_ptr
[symbol_index
]);
1218 if (coff_symbol_ptr
&& coff_symbol_ptr
->native
) {
1219 combined_entry_type
*s
= coff_symbol_ptr
->native
;
1222 if (s
->u
.syment
.n_sclass
== C_FILE
)
1224 if (last_file
!= (struct internal_syment
*)NULL
) {
1225 last_file
->n_value
= native_index
;
1227 last_file
= &(s
->u
.syment
);
1231 /* Modify the symbol values according to their section and
1234 fixup_symbol_value(coff_symbol_ptr
, &(s
->u
.syment
));
1236 for (i
= 0; i
< s
->u
.syment
.n_numaux
+ 1; i
++) {
1237 s
[i
].offset
= native_index
++;
1248 Run thorough the symbol table again, and fix it so that all pointers to
1249 entries are changed to the entries' index in the output symbol table.
1253 DEFUN(coff_mangle_symbols
,(bfd_ptr
),
1256 unsigned int symbol_count
= bfd_get_symcount(bfd_ptr
);
1257 asymbol
**symbol_ptr_ptr
= bfd_ptr
->outsymbols
;
1259 unsigned int symbol_index
;
1262 for (symbol_index
= 0; symbol_index
< symbol_count
; symbol_index
++)
1264 coff_symbol_type
*coff_symbol_ptr
= coff_symbol_from(bfd_ptr
, symbol_ptr_ptr
[symbol_index
]);
1265 if (coff_symbol_ptr
&& coff_symbol_ptr
->native
) {
1267 combined_entry_type
*s
= coff_symbol_ptr
->native
;
1273 for (i
= 0; i
< s
->u
.syment
.n_numaux
; i
++) {
1274 combined_entry_type
*a
= s
+ i
+ 1;
1276 a
->u
.auxent
.x_sym
.x_tagndx
.l
= a
->u
.auxent
.x_sym
.x_tagndx
.p
->offset
;
1279 a
->u
.auxent
.x_sym
.x_fcnary
.x_fcn
.x_endndx
.l
=
1280 a
->u
.auxent
.x_sym
.x_fcnary
.x_fcn
.x_endndx
.p
->offset
;
1289 unsigned int symbol_count
= bfd_get_symcount(bfd_ptr
);
1290 asymbol
**symbol_ptr_ptr
= bfd_ptr
->outsymbols
;
1291 struct internal_syment
*last_tagndx
= (struct internal_syment
*)NULL
;
1292 struct internal_syment
*last_file
= (struct internal_syment
*)NULL
;
1293 struct internal_syment
*last_fcn
= (struct internal_syment
*)NULL
;
1294 struct internal_syment
*block_stack
[50];
1295 struct internal_syment
**last_block
= &block_stack
[0];
1296 boolean first_time
= true;
1297 unsigned int symbol_index
;
1298 unsigned int native_index
= 0;
1300 for (symbol_index
= 0; symbol_index
< symbol_count
; symbol_index
++) {
1301 coff_symbol_type
*coff_symbol_ptr
=
1302 coff_symbol_from(bfd_ptr
, symbol_ptr_ptr
[symbol_index
]);
1303 if (coff_symbol_ptr
== (coff_symbol_type
*)NULL
) {
1305 This symbol has no coff information in it, it will take up
1306 only one slot in the output symbol table
1311 struct internal_syment
*syment
= coff_symbol_ptr
->native
;
1312 if (syment
== (struct internal_syment
*)NULL
) {
1316 /* Normalize the symbol flags */
1317 if (coff_symbol_ptr
->symbol
.flags
& BSF_FORT_COMM
) {
1318 /* a common symbol is undefined with a value */
1319 syment
->n_scnum
= N_UNDEF
;
1320 syment
->n_value
= coff_symbol_ptr
->symbol
.value
;
1322 else if (coff_symbol_ptr
->symbol
.flags
& BSF_DEBUGGING
) {
1323 syment
->n_value
= coff_symbol_ptr
->symbol
.value
;
1325 else if (coff_symbol_ptr
->symbol
.flags
& BSF_UNDEFINED
) {
1326 syment
->n_scnum
= N_UNDEF
;
1327 syment
->n_value
= 0;
1329 else if (coff_symbol_ptr
->symbol
.flags
& BSF_ABSOLUTE
) {
1330 syment
->n_scnum
= N_ABS
;
1331 syment
->n_value
= coff_symbol_ptr
->symbol
.value
;
1335 coff_symbol_ptr
->symbol
.section
->output_section
->index
+1;
1338 coff_symbol_ptr
->symbol
.value
+
1339 coff_symbol_ptr
->symbol
.section
->output_offset
+
1340 coff_symbol_ptr
->symbol
.section
->output_section
->vma
;
1344 /* If this symbol ties up something then do it */
1346 if (syment
->n_sclass
== C_FILE
&& last_file
!= (struct internal_syment
*)NULL
)
1348 last_file
->n_value
= native_index
;
1350 else if ((syment
->n_sclass
== C_EXT
1351 || syment
->n_sclass
== C_STAT
1353 || syment
->n_sclass
== C_LEAFEXT
1354 || syment
->n_sclass
== C_LEAFSTAT
1357 && last_fcn
!= (struct internal_syment
*)NULL
)
1359 union internal_auxent
*auxent
= (union internal_auxent
*)(last_fcn
+1);
1360 auxent
->x_sym
.x_fcnary
.x_fcn
.x_endndx
.l
= native_index
;
1361 last_fcn
= (struct internal_syment
*)NULL
;
1364 else if (syment
->n_sclass
== C_EOS
&& last_tagndx
!= (struct internal_syment
*)NULL
)
1366 union internal_auxent
*auxent
= (union internal_auxent
*)(last_tagndx
+1);
1367 /* Remember that we keep the native index in the offset
1368 so patch the beginning of the struct to point to this
1371 auxent->x_sym.x_tagndx = last_tagndx->_n._n_n._n_offset;*/
1372 auxent
->x_sym
.x_fcnary
.x_fcn
.x_endndx
.l
= syment
->n_numaux
+ 1 + native_index
;
1373 /* Now point the eos to the structure */
1374 auxent
= (union internal_auxent
*)(syment
+1);
1375 auxent
->x_sym
.x_tagndx
.l
= last_tagndx
->_n
._n_n
._n_offset
;
1377 else if (syment
->n_sclass
== C_BLOCK
1378 && coff_symbol_ptr
->symbol
.name
[1] == 'e')
1380 union internal_auxent
*auxent
= (union internal_auxent
*)((*(--last_block
))+1);
1381 auxent
->x_sym
.x_fcnary
.x_fcn
.x_endndx
.l
= native_index
+ syment
->n_numaux
+ 1;
1383 if (syment
->n_sclass
== C_EXT
1384 && !ISFCN(syment
->n_type
)
1385 && first_time
== true
1386 && last_file
!= (struct internal_syment
*)NULL
) {
1387 /* This is the first external symbol seen which isn't a
1388 function place it in the last .file entry */
1389 last_file
->n_value
= native_index
;
1393 if (syment
->n_sclass
== C_LEAFPROC
&&
1394 syment
->n_numaux
== 2) {
1395 union internal_auxent
*auxent
= (union internal_auxent
*)(syment
+2);
1396 /* This is the definition of a leaf proc, we'll relocate the
1398 auxent
->x_bal
.x_balntry
=
1399 coff_symbol_ptr
->symbol
.section
->output_offset
+
1400 coff_symbol_ptr
->symbol
.section
->output_section
->vma
+
1401 auxent
->x_bal
.x_balntry
;
1404 /* If this symbol needs to be tied up then remember some facts */
1405 if (syment
->n_sclass
== C_FILE
)
1409 if (syment
->n_numaux
!= 0) {
1411 If this symbol would like to point to something in the
1412 future then remember where it is
1414 if (uses_x_sym_x_tagndx_p(bfd_ptr
, syment
)) {
1416 If this is a ref to a structure then we'll tie it up
1417 now - there are never any forward refs for one
1419 if (syment
->n_sclass
== C_STRTAG
||
1420 syment
->n_sclass
== C_ENTAG
||
1421 syment
->n_sclass
== C_UNTAG
) {
1422 last_tagndx
= syment
;
1426 This is a ref to a structure - the structure must
1427 have been defined within the same file, and previous
1428 to this point, so we can deduce the new tagndx
1431 union internal_auxent
*auxent
= (union internal_auxent
*)(syment
+1);
1432 bfd
*bfd_ptr
= coff_symbol_ptr
->symbol
.the_bfd
;
1433 struct internal_syment
*base
= obj_raw_syments(bfd_ptr
);
1434 /* auxent->x_sym.x_tagndx = base[auxent->x_sym.x_tagndx]._n._n_n._n_offset;*/
1439 if (ISFCN(syment
->n_type
)) {
1442 if (syment
->n_sclass
== C_BLOCK
1443 && coff_symbol_ptr
->symbol
.name
[1] == 'b')
1445 *last_block
++ = syment
;
1448 syment
->_n
._n_n
._n_offset
= native_index
;
1449 native_index
= native_index
+ 1 + syment
->n_numaux
;
1457 static int string_size
;
1459 DEFUN(coff_fix_symbol_name
,(ignore_abfd
, symbol
, native
),
1460 bfd
*ignore_abfd AND
1462 combined_entry_type
*native
)
1464 unsigned int name_length
;
1465 union internal_auxent
*auxent
;
1466 char * name
= ( char *)(symbol
->name
);
1468 if (name
== (char *) NULL
) {
1469 /* coff symbols always have names, so we'll make one up */
1470 symbol
->name
= "strange";
1471 name
= (char *)symbol
->name
;
1473 name_length
= strlen(name
);
1475 if (native
->u
.syment
.n_sclass
== C_FILE
) {
1476 strncpy(native
->u
.syment
._n
._n_name
, ".file", SYMNMLEN
);
1477 auxent
= &(native
+1)->u
.auxent
;
1479 #ifdef COFF_LONG_FILENAMES
1480 if (name_length
<= FILNMLEN
) {
1481 strncpy(auxent
->x_file
.x_fname
, name
, FILNMLEN
);
1484 auxent
->x_file
.x_n
.x_offset
= string_size
+ 4;
1485 auxent
->x_file
.x_n
.x_zeroes
= 0;
1486 string_size
+= name_length
+ 1;
1489 strncpy(auxent
->x_file
.x_fname
, name
, FILNMLEN
);
1490 if (name_length
> FILNMLEN
) {
1491 name
[FILNMLEN
] = '\0';
1496 { /* NOT A C_FILE SYMBOL */
1497 if (name_length
<= SYMNMLEN
) {
1498 /* This name will fit into the symbol neatly */
1499 strncpy(native
->u
.syment
._n
._n_name
, symbol
->name
, SYMNMLEN
);
1502 native
->u
.syment
._n
._n_n
._n_offset
= string_size
+ 4;
1503 native
->u
.syment
._n
._n_n
._n_zeroes
= 0;
1504 string_size
+= name_length
+ 1;
1512 DEFUN(coff_write_symbol
,(abfd
, symbol
, native
, written
),
1515 combined_entry_type
*native AND
1516 unsigned int written
)
1518 unsigned int numaux
= native
->u
.syment
.n_numaux
;
1519 int type
= native
->u
.syment
.n_type
;
1520 int class = native
->u
.syment
.n_sclass
;
1524 coff_fix_symbol_name(abfd
, symbol
, native
);
1525 coff_swap_sym_out(abfd
, &native
->u
.syment
, &buf
);
1526 bfd_write((PTR
)& buf
, 1, SYMESZ
, abfd
);
1527 for (j
= 0; j
!= native
->u
.syment
.n_numaux
; j
++)
1530 bzero((PTR
)&buf
, AUXESZ
);
1531 coff_swap_aux_out(abfd
,
1532 &( (native
+ j
+ 1)->u
.auxent
), type
, class, &buf1
);
1533 bfd_write((PTR
) (&buf1
), 1, AUXESZ
, abfd
);
1536 Reuse somewhere in the symbol to keep the index
1538 set_index(symbol
, written
);
1539 return written
+ 1 + numaux
;
1544 DEFUN(coff_write_alien_symbol
,(abfd
, symbol
, written
),
1547 unsigned int written
)
1550 This symbol has been created by the loader, or come from a non
1551 coff format. It has no native element to inherit, make our
1554 combined_entry_type
*native
;
1555 combined_entry_type dummy
;
1557 native
->u
.syment
.n_type
= T_NULL
;
1559 native
->u
.syment
.n_flags
= 0;
1561 if (symbol
->flags
& BSF_ABSOLUTE
) {
1562 native
->u
.syment
.n_scnum
= N_ABS
;
1563 native
->u
.syment
.n_value
= symbol
->value
;
1565 else if (symbol
->flags
& (BSF_UNDEFINED
| BSF_FORT_COMM
)) {
1566 native
->u
.syment
.n_scnum
= N_UNDEF
;
1567 native
->u
.syment
.n_value
= symbol
->value
;
1569 else if (symbol
->flags
& BSF_DEBUGGING
) {
1571 remove name so it doesn't take up any space
1576 native
->u
.syment
.n_scnum
= symbol
->section
->output_section
->index
+
1578 native
->u
.syment
.n_value
= symbol
->value
+
1579 symbol
->section
->output_section
->vma
+
1580 symbol
->section
->output_offset
;
1582 /* Copy the any flags from the the file hdr into the symbol */
1584 coff_symbol_type
*c
= coff_symbol_from(abfd
, symbol
);
1585 if (c
!= (coff_symbol_type
*)NULL
) {
1586 native
->u
.syment
.n_flags
= c
->symbol
.the_bfd
->flags
;
1593 native
->u
.syment
.pad1
[0] = 0;
1594 native
->u
.syment
.pad1
[0] = 0;
1597 native
->u
.syment
.n_type
= 0;
1598 if (symbol
->flags
& BSF_LOCAL
)
1599 native
->u
.syment
.n_sclass
= C_STAT
;
1601 native
->u
.syment
.n_sclass
= C_EXT
;
1602 native
->u
.syment
.n_numaux
= 0;
1604 return coff_write_symbol(abfd
, symbol
, native
, written
);
1608 DEFUN(coff_write_native_symbol
,(abfd
, symbol
, written
),
1610 coff_symbol_type
*symbol AND
1611 unsigned int written
)
1614 Does this symbol have an ascociated line number - if so then
1615 make it remember this symbol index. Also tag the auxent of
1616 this symbol to point to the right place in the lineno table
1618 combined_entry_type
*native
= symbol
->native
;
1620 alent
*lineno
= symbol
->lineno
;
1623 unsigned int count
= 0;
1624 lineno
[count
].u
.offset
= written
;
1625 if (native
->u
.syment
.n_numaux
) {
1626 union internal_auxent
*a
= &((native
+1)->u
.auxent
);
1628 a
->x_sym
.x_fcnary
.x_fcn
.x_lnnoptr
=
1629 symbol
->symbol
.section
->output_section
->moving_line_filepos
;
1632 And count and relocate all other linenumbers
1635 while (lineno
[count
].line_number
) {
1636 lineno
[count
].u
.offset
+=
1637 symbol
->symbol
.section
->output_section
->vma
+
1638 symbol
->symbol
.section
->output_offset
;
1641 symbol
->symbol
.section
->output_section
->moving_line_filepos
+=
1645 return coff_write_symbol(abfd
, &( symbol
->symbol
), native
,written
);
1649 DEFUN(coff_write_symbols
,(abfd
),
1653 unsigned int limit
= bfd_get_symcount(abfd
);
1654 unsigned int written
= 0;
1661 /* Seek to the right place */
1662 bfd_seek(abfd
, obj_sym_filepos(abfd
), SEEK_SET
);
1664 /* Output all the symbols we have */
1667 for (p
= abfd
->outsymbols
, i
= 0; i
< limit
; i
++, p
++)
1669 asymbol
*symbol
= *p
;
1670 coff_symbol_type
*c_symbol
= coff_symbol_from(abfd
, symbol
);
1674 if (c_symbol
== (coff_symbol_type
*) NULL
||
1675 c_symbol
->native
== (combined_entry_type
*)NULL
)
1677 written
= coff_write_alien_symbol(abfd
, symbol
, written
);
1681 written
= coff_write_native_symbol(abfd
, c_symbol
, written
);
1686 bfd_get_symcount(abfd
) = written
;
1688 /* Now write out strings */
1690 if (string_size
!= 0)
1692 unsigned int size
= string_size
+ 4;
1695 bfd_h_put_32(abfd
, size
, buffer
);
1696 bfd_write((PTR
) buffer
, 1, sizeof(buffer
), abfd
);
1697 for (p
= abfd
->outsymbols
, i
= 0; i
< limit
; i
++, p
++)
1700 size_t name_length
= strlen(q
->name
);
1702 coff_symbol_type
* c_symbol
= coff_symbol_from(abfd
, q
);
1703 maxlen
= ((c_symbol
!= NULL
&& c_symbol
->native
!= NULL
) &&
1704 (c_symbol
->native
->u
.syment
.n_sclass
== C_FILE
)) ?
1705 FILNMLEN
: SYMNMLEN
;
1707 if (name_length
> maxlen
) {
1708 bfd_write((PTR
) (q
->name
), 1, name_length
+ 1, abfd
);
1713 /* We would normally not write anything here, but we'll write
1714 out 4 so that any stupid coff reader which tries to read
1715 the string table even when there isn't one won't croak.
1718 uint32e_type size
= 4;
1720 bfd_write((PTR
)&size
, 1, sizeof(size
), abfd
);
1726 @subsubsection Writing Relocations
1727 To write a relocations, all the back end does is step though the
1728 canonical relocation table, and create an @code{internal_reloc}. The
1729 symbol index to use is removed from the @code{offset} field in the
1730 symbol table supplied, the address comes directly from the sum of the
1731 section base address and the relocation offset and the type is dug
1732 directly from the howto field.
1734 Then the @code{internal_reloc} is swapped into the shape of an
1735 @code{external_reloc} and written out to disk.
1739 DEFUN(coff_write_relocs
,(abfd
),
1743 for (s
= abfd
->sections
; s
!= (asection
*) NULL
; s
= s
->next
) {
1745 struct external_reloc dst
;
1747 arelent
**p
= s
->orelocation
;
1748 bfd_seek(abfd
, s
->rel_filepos
, SEEK_SET
);
1749 for (i
= 0; i
< s
->reloc_count
; i
++) {
1750 struct internal_reloc n
;
1752 memset((PTR
)&n
, 0, sizeof(n
));
1753 n
.r_vaddr
= q
->address
+ s
->vma
;
1754 if (q
->sym_ptr_ptr
) {
1755 n
.r_symndx
= get_index((*(q
->sym_ptr_ptr
)));
1758 /* Work out reloc type from what is required */
1759 SELECT_RELOC(n
.r_type
, q
->howto
);
1761 n
.r_type
= q
->howto
->type
;
1763 coff_swap_reloc_out(abfd
, &n
, &dst
);
1764 bfd_write((PTR
) &n
, 1, RELSZ
, abfd
);
1768 #endif /* NO_COFF_SYMBOLS */
1770 #ifndef NO_COFF_LINENOS
1773 DEFUN(coff_write_linenumbers
,(abfd
),
1777 for (s
= abfd
->sections
; s
!= (asection
*) NULL
; s
= s
->next
) {
1778 if (s
->lineno_count
) {
1779 asymbol
**q
= abfd
->outsymbols
;
1780 bfd_seek(abfd
, s
->line_filepos
, SEEK_SET
);
1781 /* Find all the linenumbers in this section */
1784 alent
*l
= BFD_SEND(p
->the_bfd
, _get_lineno
, (p
->the_bfd
, p
));
1786 /* Found a linenumber entry, output */
1787 struct internal_lineno out
;
1789 memset( (PTR
)&out
, 0, sizeof(out
));
1791 out
.l_addr
.l_symndx
= l
->u
.offset
;
1792 coff_swap_lineno_out(abfd
, &out
, &buff
);
1793 bfd_write((PTR
) &buff
, 1, LINESZ
, abfd
);
1795 while (l
->line_number
) {
1796 out
.l_lnno
= l
->line_number
;
1797 out
.l_addr
.l_symndx
= l
->u
.offset
;
1798 coff_swap_lineno_out(abfd
, &out
, &buff
);
1799 bfd_write((PTR
) &buff
, 1, LINESZ
, abfd
);
1810 DEFUN(coff_get_lineno
,(ignore_abfd
, symbol
),
1811 bfd
*ignore_abfd AND
1814 return coffsymbol(symbol
)->lineno
;
1817 #endif /* NO_COFF_LINENOS */
1820 coff_make_empty_symbol(abfd
)
1823 coff_symbol_type
*new = (coff_symbol_type
*) bfd_alloc(abfd
, sizeof(coff_symbol_type
));
1825 bfd_error
= no_memory
;
1829 new->lineno
= (alent
*) NULL
;
1830 new->symbol
.the_bfd
= abfd
;
1831 return &new->symbol
;
1834 #ifndef NO_COFF_SYMBOLS
1837 DEFUN(coff_print_symbol
,(ignore_abfd
, filep
, symbol
, how
),
1838 bfd
*ignore_abfd AND
1841 bfd_print_symbol_type how
)
1843 FILE *file
= (FILE *)filep
;
1845 case bfd_print_symbol_name
:
1846 fprintf(file
, "%s", symbol
->name
);
1848 case bfd_print_symbol_more
:
1849 fprintf(file
, "coff %lx %lx", (unsigned long) coffsymbol(symbol
)->native
,
1850 (unsigned long) coffsymbol(symbol
)->lineno
);
1852 case bfd_print_symbol_all
:
1854 CONST
char *section_name
= symbol
->section
== (asection
*) NULL
?
1855 "*abs" : symbol
->section
->name
;
1856 bfd_print_symbol_vandf((PTR
) file
, symbol
);
1858 fprintf(file
, " %-5s %s %s %s",
1860 coffsymbol(symbol
)->native
? "n" : "g",
1861 coffsymbol(symbol
)->lineno
? "l" : " ",
1870 #endif /* NO_COFF_SYMBOLS */
1872 /* Set flags and magic number of a coff file from architecture and machine
1873 type. Result is true if we can represent the arch&type, false if not. */
1876 DEFUN(coff_set_flags
,(abfd
, magicp
, flagsp
),
1878 unsigned *magicp AND
1879 unsigned short *flagsp
)
1881 switch (bfd_get_arch(abfd
)) {
1889 *magicp
= I960ROMAGIC
;
1891 ((bfd_get_file_flags(abfd) & WP_TEXT) ? I960ROMAGIC :
1892 I960RWMAGIC); FIXME???
1894 switch (bfd_get_mach(abfd
)) {
1895 case bfd_mach_i960_core
:
1898 case bfd_mach_i960_kb_sb
:
1901 case bfd_mach_i960_mc
:
1904 case bfd_mach_i960_xa
:
1907 case bfd_mach_i960_ca
:
1910 case bfd_mach_i960_ka_sa
:
1923 *magicp
= MIPS_MAGIC_2
;
1929 *magicp
= I386MAGIC
;
1934 *magicp
= MC68MAGIC
;
1940 *magicp
= MC88OMAGIC
;
1945 #ifdef A29K_MAGIC_BIG
1947 if (abfd
->xvec
->byteorder_big_p
)
1948 *magicp
= A29K_MAGIC_BIG
;
1950 *magicp
= A29K_MAGIC_LITTLE
;
1955 default: /* Unknown architecture */
1956 /* return false; -- fall through to "return false" below, to avoid
1957 "statement never reached" errors on the one below. */
1966 DEFUN(coff_set_arch_mach
,(abfd
, arch
, machine
),
1968 enum bfd_architecture arch AND
1969 unsigned long machine
)
1972 unsigned short dummy2
;
1973 bfd_default_set_arch_mach(abfd
, arch
, machine
);
1975 if (arch
!= bfd_arch_unknown
&&
1976 coff_set_flags(abfd
, &dummy1
, &dummy2
) != true)
1977 return false; /* We can't represent this type */
1978 return true; /* We're easy ... */
1982 /* Calculate the file position for each section. */
1985 DEFUN(coff_compute_section_file_positions
,(abfd
),
1989 file_ptr sofar
= FILHSZ
;
1990 if (bfd_get_start_address(abfd
)) {
1992 A start address may have been added to the original file. In this
1993 case it will need an optional header to record it.
1995 abfd
->flags
|= EXEC_P
;
1997 if (abfd
->flags
& EXEC_P
)
2001 sofar
+= abfd
->section_count
* SCNHSZ
;
2002 for (current
= abfd
->sections
;
2003 current
!= (asection
*)NULL
;
2004 current
= current
->next
) {
2005 /* Only deal with sections which have contents */
2006 if (!(current
->flags
& SEC_HAS_CONTENTS
))
2009 /* Align the sections in the file to the same boundary on
2010 which they are aligned in virtual memory. I960 doesn't
2011 do this (FIXME) so we can stay in sync with Intel. 960
2012 doesn't yet page from files... */
2014 sofar
= ALIGN(sofar
, 1 << current
->alignment_power
);
2016 /* FIXME, in demand paged files, the low order bits of the file
2017 offset must match the low order bits of the virtual address.
2018 "Low order" is apparently implementation defined. Add code
2019 here to round sofar up to match the virtual address. */
2021 current
->filepos
= sofar
;
2022 sofar
+= current
->size
;
2024 obj_relocbase(abfd
) = sofar
;
2033 DEFUN(coff_write_object_contents
,(abfd
),
2037 boolean hasrelocs
= false;
2038 boolean haslinno
= false;
2039 file_ptr reloc_base
;
2040 file_ptr lineno_base
;
2044 unsigned long reloc_size
= 0;
2045 unsigned long lnno_size
= 0;
2046 asection
*text_sec
= NULL
;
2047 asection
*data_sec
= NULL
;
2048 asection
*bss_sec
= NULL
;
2050 struct internal_filehdr internal_f
;
2051 struct internal_aouthdr internal_a
;
2054 bfd_error
= system_call_error
;
2057 if(abfd
->output_has_begun
== false) {
2058 coff_compute_section_file_positions(abfd
);
2061 if (abfd
->sections
!= (asection
*)NULL
) {
2062 scn_base
= abfd
->sections
->filepos
;
2067 if (bfd_seek(abfd
, scn_base
, SEEK_SET
) != 0)
2069 reloc_base
= obj_relocbase(abfd
);
2071 /* Make a pass through the symbol table to count line number entries and
2072 put them into the correct asections */
2074 #ifndef NO_COFF_LINENOS
2075 coff_count_linenumbers(abfd
);
2077 data_base
= scn_base
;
2079 /* Work out the size of the reloc and linno areas */
2081 for (current
= abfd
->sections
; current
!= NULL
; current
= current
->next
) {
2082 reloc_size
+= current
->reloc_count
* RELSZ
;
2083 #ifndef NO_COFF_LINENOS
2084 lnno_size
+= current
->lineno_count
* LINESZ
;
2086 data_base
+= SCNHSZ
;
2089 lineno_base
= reloc_base
+ reloc_size
;
2090 sym_base
= lineno_base
+ lnno_size
;
2092 /* Indicate in each section->line_filepos its actual file address */
2093 for (current
= abfd
->sections
; current
!= NULL
; current
= current
->next
) {
2094 if (current
->lineno_count
) {
2095 current
->line_filepos
= lineno_base
;
2096 current
->moving_line_filepos
= lineno_base
;
2097 #ifndef NO_COFF_LINENOS
2098 lineno_base
+= current
->lineno_count
* LINESZ
;
2102 current
->line_filepos
= 0;
2104 if (current
->reloc_count
) {
2105 current
->rel_filepos
= reloc_base
;
2106 reloc_base
+= current
->reloc_count
* sizeof(struct internal_reloc
);
2109 current
->rel_filepos
= 0;
2113 /* Write section headers to the file. */
2116 (file_ptr
) ((abfd
->flags
& EXEC_P
) ?
2117 (FILHSZ
+ AOUTSZ
) : FILHSZ
),
2122 unsigned int pad
= abfd
->flags
& D_PAGED
? data_base
: 0;
2124 unsigned int pad
= 0;
2126 for (current
= abfd
->sections
; current
!= NULL
; current
= current
->next
) {
2127 struct internal_scnhdr section
;
2128 strncpy(&(section
.s_name
[0]), current
->name
, 8);
2129 section
.s_vaddr
= current
->vma
+ pad
;
2130 section
.s_paddr
= current
->vma
+ pad
;
2131 section
.s_size
= current
->size
- pad
;
2133 If this section has no size or is unloadable then the scnptr
2136 if (current
->size
- pad
== 0 ||
2137 (current
->flags
& SEC_LOAD
) == 0) {
2138 section
.s_scnptr
= 0;
2142 section
.s_scnptr
= current
->filepos
;
2144 section
.s_relptr
= current
->rel_filepos
;
2145 section
.s_lnnoptr
= current
->line_filepos
;
2146 section
.s_nreloc
= current
->reloc_count
;
2147 section
.s_nlnno
= current
->lineno_count
;
2148 if (current
->reloc_count
!= 0)
2150 if (current
->lineno_count
!= 0)
2153 section
.s_flags
= sec_to_styp_flags(current
->name
,current
->flags
);
2155 if (!strcmp(current
->name
, _TEXT
)) {
2157 } else if (!strcmp(current
->name
, _DATA
)) {
2159 } else if (!strcmp(current
->name
, _BSS
)) {
2164 section
.s_align
= (current
->alignment_power
2165 ? 1 << current
->alignment_power
2172 coff_swap_scnhdr_out(abfd
, §ion
, &buff
);
2173 bfd_write((PTR
) (&buff
), 1, SCNHSZ
, abfd
);
2180 /* OK, now set up the filehdr... */
2181 internal_f
.f_nscns
= abfd
->section_count
;
2183 We will NOT put a fucking timestamp in the header here. Every time you
2184 put it back, I will come in and take it out again. I'm sorry. This
2185 field does not belong here. We fill it with a 0 so it compares the
2186 same but is not a reasonable time. -- gnu@cygnus.com
2189 Well, I like it, so I'm conditionally compiling it in.
2192 #ifdef COFF_TIMESTAMP
2193 internal_f
.f_timdat
= time(0);
2195 internal_f
.f_timdat
= 0;
2198 if (bfd_get_symcount(abfd
) != 0)
2199 internal_f
.f_symptr
= sym_base
;
2201 internal_f
.f_symptr
= 0;
2203 internal_f
.f_flags
= 0;
2205 if (abfd
->flags
& EXEC_P
)
2206 internal_f
.f_opthdr
= AOUTSZ
;
2208 internal_f
.f_opthdr
= 0;
2211 internal_f
.f_flags
|= F_RELFLG
;
2213 internal_f
.f_flags
|= F_LNNO
;
2214 if (0 == bfd_get_symcount(abfd
))
2215 internal_f
.f_flags
|= F_LSYMS
;
2216 if (abfd
->flags
& EXEC_P
)
2217 internal_f
.f_flags
|= F_EXEC
;
2219 internal_f
.f_flags
|= F_AR32W
;
2221 if (!abfd
->xvec
->byteorder_big_p
)
2222 internal_f
.f_flags
|= F_AR32WR
;
2225 FIXME, should do something about the other byte orders and
2229 /* Set up architecture-dependent stuff */
2231 { unsigned int magic
= 0;
2232 unsigned short flags
= 0;
2233 coff_set_flags(abfd
, &magic
, &flags
);
2234 internal_f
.f_magic
= magic
;
2235 internal_f
.f_flags
|= flags
;
2236 /* ...and the "opt"hdr... */
2239 # ifdef ULTRA3 /* NYU's machine */
2240 /* FIXME: This is a bogus check. I really want to see if there
2241 * is a .shbss or a .shdata section, if so then set the magic
2242 * number to indicate a shared data executable.
2244 if (internal_f
.f_nscns
>= 7)
2245 internal_a
.magic
= SHMAGIC
; /* Shared magic */
2247 # endif /* ULTRA3 */
2248 internal_a
.magic
= NMAGIC
; /* Assume separate i/d */
2249 #define __A_MAGIC_SET__
2252 internal_a
.magic
= (magic
== I960ROMAGIC
? NMAGIC
: OMAGIC
);
2253 #define __A_MAGIC_SET__
2256 #define __A_MAGIC_SET__
2257 internal_a
.magic
= PAGEMAGICBCS
;
2260 #if M68 || I386 || MIPS
2261 #define __A_MAGIC_SET__
2262 /* Never was anything here for the 68k */
2265 #ifndef __A_MAGIC_SET__
2266 # include "Your aouthdr magic number is not being set!"
2268 # undef __A_MAGIC_SET__
2271 /* Now should write relocs, strings, syms */
2272 obj_sym_filepos(abfd
) = sym_base
;
2274 #ifndef NO_COFF_SYMBOLS
2275 if (bfd_get_symcount(abfd
) != 0) {
2276 coff_renumber_symbols(abfd
);
2277 coff_mangle_symbols(abfd
);
2278 coff_write_symbols(abfd
);
2279 coff_write_linenumbers(abfd
);
2280 coff_write_relocs(abfd
);
2282 #endif /* NO_COFF_SYMBOLS */
2284 internal_a
.tsize
= text_sec
->size
;
2285 internal_a
.text_start
=text_sec
->size
? text_sec
->vma
: 0;
2288 internal_a
.dsize
= data_sec
->size
;
2289 internal_a
.data_start
= data_sec
->size
? data_sec
->vma
: 0;
2292 internal_a
.bsize
= bss_sec
->size
;
2295 internal_a
.entry
= bfd_get_start_address(abfd
);
2296 internal_f
.f_nsyms
= bfd_get_symcount(abfd
);
2298 /* now write them */
2299 if (bfd_seek(abfd
, 0L, SEEK_SET
) != 0)
2303 coff_swap_filehdr_out(abfd
, &internal_f
, &buff
);
2304 bfd_write((PTR
) &buff
, 1, FILHSZ
, abfd
);
2306 if (abfd
->flags
& EXEC_P
) {
2308 coff_swap_aouthdr_out(abfd
, &internal_a
, &buff
);
2309 bfd_write((PTR
) &buff
, 1, AOUTSZ
, abfd
);
2314 #ifndef NO_COFF_SYMBOLS
2317 this function transforms the offsets into the symbol table into
2318 pointers to syments.
2323 DEFUN(coff_pointerize_aux
,(ignore_abfd
, table_base
, type
, class, auxent
),
2324 bfd
*ignore_abfd AND
2325 combined_entry_type
*table_base AND
2328 combined_entry_type
*auxent
)
2330 /* Don't bother if this is a file or a section */
2331 if (class == C_STAT
&& type
== T_NULL
) return;
2332 if (class == C_FILE
) return;
2334 /* Otherwise patch up */
2335 if (ISFCN(type
) || ISTAG(class) || class == C_BLOCK
) {
2336 auxent
->u
.auxent
.x_sym
.x_fcnary
.x_fcn
.x_endndx
.p
= table_base
+
2337 auxent
->u
.auxent
.x_sym
.x_fcnary
.x_fcn
.x_endndx
.l
;
2338 auxent
->fix_end
= 1;
2340 if (auxent
->u
.auxent
.x_sym
.x_tagndx
.l
!= 0) {
2341 auxent
->u
.auxent
.x_sym
.x_tagndx
.p
= table_base
+ auxent
->u
.auxent
.x_sym
.x_tagndx
.l
;
2342 auxent
->fix_tag
= 1;
2346 #endif /* NO_COFF_SYMBOLS */
2349 DEFUN(coff_set_section_contents
,(abfd
, section
, location
, offset
, count
),
2354 bfd_size_type count
)
2356 if (abfd
->output_has_begun
== false) /* set by bfd.c handler */
2357 coff_compute_section_file_positions(abfd
);
2359 bfd_seek(abfd
, (file_ptr
) (section
->filepos
+ offset
), SEEK_SET
);
2362 return (bfd_write(location
, 1, count
, abfd
) == count
) ? true : false;
2368 coff_close_and_cleanup(abfd
)
2371 if (!bfd_read_p(abfd
))
2372 switch (abfd
->format
) {
2374 if (!_bfd_write_archive_contents(abfd
))
2378 if (!coff_write_object_contents(abfd
))
2382 bfd_error
= invalid_operation
;
2386 /* We depend on bfd_close to free all the memory on the obstack. */
2387 /* FIXME if bfd_release is not using obstacks! */
2393 buy_and_read(abfd
, where
, seek_direction
, size
)
2399 PTR area
= (PTR
) bfd_alloc(abfd
, size
);
2401 bfd_error
= no_memory
;
2404 bfd_seek(abfd
, where
, seek_direction
);
2405 if (bfd_read(area
, 1, size
, abfd
) != size
) {
2406 bfd_error
= system_call_error
;
2410 } /* buy_and_read() */
2413 #ifndef NO_COFF_SYMBOLS
2416 DEFUN(build_string_table
,(abfd
),
2419 char string_table_size_buffer
[4];
2420 unsigned int string_table_size
;
2423 At this point we should be "seek"'d to the end of the
2424 symbols === the symbol table size.
2427 if (bfd_read((char *) string_table_size_buffer
,
2428 sizeof(string_table_size_buffer
),
2429 1, abfd
) != sizeof(string_table_size
)) {
2430 bfd_error
= system_call_error
;
2434 string_table_size
= bfd_h_get_32(abfd
, (bfd_byte
*) string_table_size_buffer
);
2436 if ((string_table
= (PTR
) bfd_alloc(abfd
, string_table_size
-= 4)) == NULL
) {
2437 bfd_error
= no_memory
;
2439 } /* on mallocation error */
2440 if (bfd_read(string_table
, string_table_size
, 1, abfd
) != string_table_size
) {
2441 bfd_error
= system_call_error
;
2444 return string_table
;
2447 /* Return a pointer to a malloc'd copy of 'name'. 'name' may not be
2448 \0-terminated, but will not exceed 'maxlen' characters. The copy *will*
2449 be \0-terminated. */
2451 DEFUN(copy_name
,(abfd
, name
, maxlen
),
2459 for (len
= 0; len
< maxlen
; ++len
) {
2460 if (name
[len
] == '\0') {
2465 if ((newname
= (PTR
) bfd_alloc(abfd
, len
+1)) == NULL
) {
2466 bfd_error
= no_memory
;
2469 strncpy(newname
, name
, len
);
2470 newname
[len
] = '\0';
2476 read a symbol table into freshly mallocated memory, swap it, and knit the
2477 symbol names into a normalized form. By normalized here I mean that all
2478 symbols have an n_offset pointer that points to a NULL terminated string.
2479 Oh, and the first symbol MUST be a C_FILE. If there wasn't one there
2480 before, put one there.
2483 static combined_entry_type
*
2484 DEFUN(get_normalized_symtab
,(abfd
),
2488 combined_entry_type
*internal
;
2489 combined_entry_type
*internal_ptr
;
2490 combined_entry_type
*internal_end
;
2494 char *string_table
= NULL
;
2498 unsigned int raw_size
;
2499 if (obj_raw_syments(abfd
) != (combined_entry_type
*)NULL
) {
2500 return obj_raw_syments(abfd
);
2502 if ((size
= bfd_get_symcount(abfd
) * sizeof(combined_entry_type
)) == 0) {
2503 bfd_error
= no_symbols
;
2507 internal
= (combined_entry_type
*)bfd_alloc(abfd
, size
);
2508 internal_end
= internal
+ bfd_get_symcount(abfd
);
2510 raw_size
= bfd_get_symcount(abfd
) * SYMESZ
;
2511 raw
= (SYMENT
*)bfd_alloc(abfd
,raw_size
);
2513 if (bfd_seek(abfd
, obj_sym_filepos(abfd
), SEEK_SET
) == -1
2514 || bfd_read((PTR
)raw
, raw_size
, 1, abfd
) != raw_size
) {
2515 bfd_error
= system_call_error
;
2518 /* mark the end of the symbols */
2519 raw_end
= raw
+ bfd_get_symcount(abfd
);
2521 FIXME SOMEDAY. A string table size of zero is very weird, but
2522 probably possible. If one shows up, it will probably kill us.
2525 /* Swap all the raw entries */
2526 for (raw_src
= raw
, internal_ptr
= internal
; raw_src
< raw_end
; raw_src
++, internal_ptr
++) {
2528 coff_swap_sym_in(abfd
, (char *)raw_src
, (char *)&internal_ptr
->u
.syment
);
2529 internal_ptr
->fix_tag
= 0;
2530 internal_ptr
->fix_end
= 0;
2532 for (i
= internal_ptr
->u
.syment
.n_numaux
; i
; --i
, raw_src
++, internal_ptr
++) {
2533 (internal_ptr
+1)->fix_tag
= 0;
2534 (internal_ptr
+1)->fix_end
= 0;
2536 coff_swap_aux_in(abfd
, (char *)(raw_src
+1), internal_ptr
->u
.syment
.n_type
,
2537 internal_ptr
->u
.syment
.n_sclass
, & (internal_ptr
+1)->u
.auxent
);
2539 coff_pointerize_aux(abfd
,
2541 internal_ptr
->u
.syment
.n_type
,
2542 internal_ptr
->u
.syment
.n_sclass
,
2547 /* Free all the raw stuff */
2548 bfd_release(abfd
, raw
);
2550 for (internal_ptr
= internal
; internal_ptr
< internal_end
;
2553 if (internal_ptr
->u
.syment
.n_sclass
== C_FILE
) {
2554 /* make a file symbol point to the name in the auxent, since
2555 the text ".file" is redundant */
2556 if ((internal_ptr
+1)->u
.auxent
.x_file
.x_n
.x_zeroes
== 0) {
2557 /* the filename is a long one, point into the string table
2559 if (string_table
== NULL
) {
2560 string_table
= build_string_table(abfd
);
2563 internal_ptr
->u
.syment
._n
._n_n
._n_offset
=
2564 (int) (string_table
- 4 +
2565 (internal_ptr
+1)->u
.auxent
.x_file
.x_n
.x_offset
);
2568 /* ordinary short filename, put into memory anyway */
2569 internal_ptr
->u
.syment
._n
._n_n
._n_offset
= (int)
2570 copy_name(abfd
, (internal_ptr
+1)->u
.auxent
.x_file
.x_fname
, FILNMLEN
);
2575 if (internal_ptr
->u
.syment
._n
._n_n
._n_zeroes
!= 0) {
2577 This is a "short" name. Make it long.
2579 unsigned long i
= 0;
2580 char *newstring
= NULL
;
2582 find the length of this string without walking into memory
2586 for (i
= 0; i
< 8; ++i
) {
2587 if (internal_ptr
->u
.syment
._n
._n_name
[i
] == '\0') {
2589 } /* if end of string */
2590 } /* possible lengths of this string. */
2592 if ((newstring
= (PTR
) bfd_alloc(abfd
, ++i
)) == NULL
) {
2593 bfd_error
= no_memory
;
2596 bzero(newstring
, i
);
2597 strncpy(newstring
, internal_ptr
->u
.syment
._n
._n_name
, i
-1);
2598 internal_ptr
->u
.syment
._n
._n_n
._n_offset
= (int) newstring
;
2599 internal_ptr
->u
.syment
._n
._n_n
._n_zeroes
= 0;
2603 /* This is a long name already. Just point it at the string in memory. */
2604 if (string_table
== NULL
) {
2605 string_table
= build_string_table(abfd
);
2607 internal_ptr
->u
.syment
._n
._n_n
._n_offset
=
2608 (int) (string_table
- 4 + internal_ptr
->u
.syment
._n
._n_n
._n_offset
);
2611 internal_ptr
+= internal_ptr
->u
.syment
.n_numaux
;
2614 obj_raw_syments(abfd
) = internal
;
2615 obj_string_table(abfd
) = string_table
;
2618 } /* get_normalized_symtab() */
2620 #endif /* NO_COFF_SYMBOLS */
2624 DEFUN(section_from_bfd_index
,(abfd
, index
),
2629 struct sec
*answer
= abfd
->sections
;
2631 answer
= answer
->next
;
2638 #ifndef NO_COFF_LINENOS
2641 @subsubsection Reading Linenumbers
2642 Createing the linenumber table is done by reading in the entire coff
2643 linenumber table, and creating another table for internal use.
2645 A coff line number table is structured so that each
2646 function is marked as having a line number of 0. Each line within the
2647 function is an offset from the first line in the function. The base of
2648 the line number information for the table is stored in the symbol
2649 associated with the function.
2651 The information is copied from the external to the internal table, and
2652 each symbol which marks a function is marked by pointing its...
2654 **How does this work ?**
2659 coff_slurp_line_table(abfd
, asect
)
2663 LINENO
*native_lineno
;
2664 alent
*lineno_cache
;
2666 BFD_ASSERT(asect
->lineno
== (alent
*) NULL
);
2668 native_lineno
= (LINENO
*) buy_and_read(abfd
,
2669 asect
->line_filepos
,
2672 asect
->lineno_count
));
2674 (alent
*) bfd_alloc(abfd
, (size_t) ((asect
->lineno_count
+ 1) * sizeof(alent
)));
2675 if (lineno_cache
== NULL
) {
2676 bfd_error
= no_memory
;
2679 unsigned int counter
= 0;
2680 alent
*cache_ptr
= lineno_cache
;
2681 LINENO
*src
= native_lineno
;
2683 while (counter
< asect
->lineno_count
) {
2684 struct internal_lineno dst
;
2685 coff_swap_lineno_in(abfd
, src
, &dst
);
2686 cache_ptr
->line_number
= dst
.l_lnno
;
2688 if (cache_ptr
->line_number
== 0) {
2689 coff_symbol_type
*sym
=
2690 (coff_symbol_type
*) (dst
.l_addr
.l_symndx
2691 + obj_symbol_slew(abfd
)
2692 + obj_raw_syments(abfd
))->u
.syment
._n
._n_n
._n_zeroes
;
2693 cache_ptr
->u
.sym
= (asymbol
*) sym
;
2694 sym
->lineno
= cache_ptr
;
2697 cache_ptr
->u
.offset
= dst
.l_addr
.l_paddr
2698 - bfd_section_vma(abfd
, asect
);
2699 } /* If no linenumber expect a symbol index */
2705 cache_ptr
->line_number
= 0;
2708 asect
->lineno
= lineno_cache
;
2709 /* FIXME, free native_lineno here, or use alloca or something. */
2711 } /* coff_slurp_line_table() */
2713 #endif /* NO_COFF_LINENOS */
2715 #ifndef NO_COFF_LINENOS
2718 DEFUN(coff_slurp_symbol_table
,(abfd
),
2721 combined_entry_type
*native_symbols
;
2722 coff_symbol_type
*cached_area
;
2723 unsigned int *table_ptr
;
2725 unsigned int number_of_symbols
= 0;
2726 if (obj_symbols(abfd
))
2728 bfd_seek(abfd
, obj_sym_filepos(abfd
), SEEK_SET
);
2730 /* Read in the symbol table */
2731 if ((native_symbols
= get_normalized_symtab(abfd
)) == NULL
) {
2736 /* Allocate enough room for all the symbols in cached form */
2738 (coff_symbol_type
*)
2739 bfd_alloc(abfd
, (size_t) (bfd_get_symcount(abfd
) * sizeof(coff_symbol_type
)));
2741 if (cached_area
== NULL
) {
2742 bfd_error
= no_memory
;
2747 bfd_alloc(abfd
, (size_t) (bfd_get_symcount(abfd
) * sizeof(unsigned int)));
2749 if (table_ptr
== NULL
) {
2750 bfd_error
= no_memory
;
2753 coff_symbol_type
*dst
= cached_area
;
2754 unsigned int last_native_index
= bfd_get_symcount(abfd
);
2755 unsigned int this_index
= 0;
2756 while (this_index
< last_native_index
) {
2757 combined_entry_type
*src
= native_symbols
+ this_index
;
2758 table_ptr
[this_index
] = number_of_symbols
;
2759 dst
->symbol
.the_bfd
= abfd
;
2761 dst
->symbol
.name
= (char *)(src
->u
.syment
._n
._n_n
._n_offset
);
2763 We use the native name field to point to the cached field
2765 src
->u
.syment
._n
._n_n
._n_zeroes
= (int) dst
;
2766 dst
->symbol
.section
= section_from_bfd_index(abfd
,
2767 src
->u
.syment
.n_scnum
);
2768 switch (src
->u
.syment
.n_sclass
) {
2772 dst
->symbol
.value
= src
->u
.syment
.n_value
- dst
->symbol
.section
->vma
;
2773 dst
->symbol
.flags
= BSF_EXPORT
| BSF_GLOBAL
;
2774 dst
->symbol
.flags
|= BSF_NOT_AT_END
;
2776 /* Fall through to next case */
2781 if ((src
->u
.syment
.n_scnum
) == 0) {
2782 if ((src
->u
.syment
.n_value
) == 0) {
2783 dst
->symbol
.flags
= BSF_UNDEFINED
;
2784 dst
->symbol
.value
= 0;
2787 dst
->symbol
.flags
= BSF_FORT_COMM
;
2788 dst
->symbol
.value
= (src
->u
.syment
.n_value
);
2793 Base the value as an index from the base of the
2796 if (dst
->symbol
.section
== (asection
*) NULL
) {
2797 dst
->symbol
.flags
= BSF_EXPORT
| BSF_GLOBAL
| BSF_ABSOLUTE
;
2798 dst
->symbol
.value
= src
->u
.syment
.n_value
;
2801 dst
->symbol
.flags
= BSF_EXPORT
| BSF_GLOBAL
;
2802 dst
->symbol
.value
= src
->u
.syment
.n_value
- dst
->symbol
.section
->vma
;
2804 if (ISFCN((src
->u
.syment
.n_type
))) {
2806 A function ext does not go at the end of a file
2808 dst
->symbol
.flags
|= BSF_NOT_AT_END
;
2813 case C_STAT
: /* static */
2815 case C_LEAFSTAT
: /* static leaf procedure */
2817 case C_LABEL
: /* label */
2818 if (src
->u
.syment
.n_scnum
== -2)
2819 dst
->symbol
.flags
= BSF_DEBUGGING
;
2821 dst
->symbol
.flags
= BSF_LOCAL
;
2823 Base the value as an index from the base of the section, if
2826 if (dst
->symbol
.section
)
2827 dst
->symbol
.value
= (src
->u
.syment
.n_value
) -
2828 dst
->symbol
.section
->vma
;
2830 dst
->symbol
.value
= (src
->u
.syment
.n_value
) ;
2833 case C_MOS
: /* member of structure */
2834 case C_EOS
: /* end of structure */
2835 #ifdef NOTDEF /* C_AUTOARG has the same value */
2837 case C_GLBLREG
: /* A29k-specific storage class */
2840 case C_REGPARM
: /* register parameter */
2841 case C_REG
: /* register variable */
2843 case C_AUTOARG
: /* 960-specific storage class */
2845 case C_TPDEF
: /* type definition */
2848 case C_AUTO
: /* automatic variable */
2849 case C_FIELD
: /* bit field */
2850 case C_ENTAG
: /* enumeration tag */
2851 case C_MOE
: /* member of enumeration */
2852 case C_MOU
: /* member of union */
2853 case C_UNTAG
: /* union tag */
2855 dst
->symbol
.flags
= BSF_DEBUGGING
;
2856 dst
->symbol
.value
= (src
->u
.syment
.n_value
);
2859 case C_FILE
: /* file name */
2860 case C_STRTAG
: /* structure tag */
2861 dst
->symbol
.flags
= BSF_DEBUGGING
;
2862 dst
->symbol
.value
= (src
->u
.syment
.n_value
);
2865 case C_BLOCK
: /* ".bb" or ".eb" */
2866 case C_FCN
: /* ".bf" or ".ef" */
2867 case C_EFCN
: /* physical end of function */
2868 dst
->symbol
.flags
= BSF_LOCAL
;
2870 Base the value as an index from the base of the section
2872 dst
->symbol
.value
= (src
->u
.syment
.n_value
) - dst
->symbol
.section
->vma
;
2876 case C_EXTDEF
: /* external definition */
2877 case C_ULABEL
: /* undefined label */
2878 case C_USTATIC
: /* undefined static */
2879 case C_LINE
: /* line # reformatted as symbol table entry */
2880 case C_ALIAS
: /* duplicate tag */
2881 case C_HIDDEN
: /* ext symbol in dmert public lib */
2885 fprintf(stderr
,"Unrecognized storage class %d\n",
2886 src
->u
.syment
.n_sclass
);
2888 dst
->symbol
.flags
= BSF_DEBUGGING
;
2889 dst
->symbol
.value
= (src
->u
.syment
.n_value
);
2894 BFD_ASSERT(dst
->symbol
.flags
!= 0);
2898 dst
->symbol
.udata
= 0;
2899 dst
->lineno
= (alent
*) NULL
;
2900 this_index
+= (src
->u
.syment
.n_numaux
) + 1;
2902 number_of_symbols
++;
2903 } /* walk the native symtab */
2904 } /* bfdize the native symtab */
2906 obj_symbols(abfd
) = cached_area
;
2907 obj_raw_syments(abfd
) = native_symbols
;
2909 bfd_get_symcount(abfd
) = number_of_symbols
;
2910 obj_convert(abfd
) = table_ptr
;
2911 /* Slurp the line tables for each section too */
2916 coff_slurp_line_table(abfd
, p
);
2921 } /* coff_slurp_symbol_table() */
2924 coff_get_symtab_upper_bound(abfd
)
2927 if (!coff_slurp_symbol_table(abfd
))
2930 return (bfd_get_symcount(abfd
) + 1) * (sizeof(coff_symbol_type
*));
2935 coff_get_symtab(abfd
, alocation
)
2937 asymbol
**alocation
;
2939 unsigned int counter
= 0;
2940 coff_symbol_type
*symbase
;
2941 coff_symbol_type
**location
= (coff_symbol_type
**) (alocation
);
2942 if (!coff_slurp_symbol_table(abfd
))
2945 for (symbase
= obj_symbols(abfd
); counter
++ < bfd_get_symcount(abfd
);)
2946 *(location
++) = symbase
++;
2948 return bfd_get_symcount(abfd
);
2951 #endif /* NO_COFF_SYMBOLS */
2954 coff_get_reloc_upper_bound(abfd
, asect
)
2958 if (bfd_get_format(abfd
) != bfd_object
) {
2959 bfd_error
= invalid_operation
;
2962 return (asect
->reloc_count
+ 1) * sizeof(arelent
*);
2966 @subsubsection Reading Relocations
2967 Coff relocations are easily transformed into the internal BFD form
2970 Reading a coff relocation table is done in the following stages:
2973 The entire coff relocation table is read into memory.
2975 Each relocation is processed in turn, first it is swapped from the
2976 external to the internal form.
2978 The symbol referenced in the relocation's symbol index is turned into
2979 a pointer into the canonical symbol table. Note that this table is the
2980 same as the one returned by a call to @code{bfd_canonicalize_symtab}.
2981 The back end will call the routine and save the result if a
2982 canonicalization hasn't been done.
2984 The reloc index is turned into a pointer to a howto structure, in a
2985 back end specific way. For instance, the 386 and 960 use the
2986 @code{r_type} to directly produce an index into a howto table vector;
2987 the 88k subtracts a number from the @code{r_type} field and creates an
2993 DEFUN(coff_slurp_reloc_table
,(abfd
, asect
, symbols
),
2998 RELOC
*native_relocs
;
2999 arelent
*reloc_cache
;
3000 if (asect
->relocation
)
3002 if (asect
->reloc_count
== 0)
3004 #ifndef NO_COFF_SYMBOLS
3005 if (!coff_slurp_symbol_table(abfd
))
3009 (RELOC
*) buy_and_read(abfd
,
3013 asect
->reloc_count
));
3014 reloc_cache
= (arelent
*)
3015 bfd_alloc(abfd
, (size_t) (asect
->reloc_count
* sizeof(arelent
)));
3017 if (reloc_cache
== NULL
) {
3018 bfd_error
= no_memory
;
3023 for (cache_ptr
= reloc_cache
,
3024 src
= native_relocs
;
3025 cache_ptr
< reloc_cache
+ asect
->reloc_count
;
3028 struct internal_reloc dst
;
3030 bfd_swap_reloc_in(abfd
, src
, &dst
);
3032 dst
.r_symndx
+= obj_symbol_slew(abfd
);
3033 cache_ptr
->sym_ptr_ptr
= symbols
+ obj_convert(abfd
)[dst
.r_symndx
];
3035 /* AMD has two relocation entries for the 'consth' instruction.
3036 * The first is R_IHIHALF (part 1), the second is R_IHCONST
3037 * (part 2). The second entry's r_symndx does not contain
3038 * an index to a symbol but rather a value (apparently).
3039 * Also, see the ifdef below for saving the r_symndx value in addend.
3041 if (dst
.r_type
== R_IHCONST
) {
3045 ptr
= *(cache_ptr
->sym_ptr_ptr
);
3046 cache_ptr
->address
= dst
.r_vaddr
;
3048 The symbols definitions that we have read in have been
3049 relocated as if their sections started at 0. But the offsets
3050 refering to the symbols in the raw data have not been
3051 modified, so we have to have a negative addend to compensate.
3053 Note that symbols which used to be common must be left alone
3056 if (ptr
&& ptr
->the_bfd
== abfd
3057 && ptr
->section
!= (asection
*) NULL
3058 && ((ptr
->flags
& BSF_OLD_COMMON
)== 0))
3061 cache_ptr
->addend
= -(ptr
->section
->vma
+ ptr
->value
);
3063 cache_ptr
->addend
= 0;
3068 cache_ptr
->addend
= 0;
3071 cache_ptr
->address
-= asect
->vma
;
3073 cache_ptr
->section
= (asection
*) NULL
;
3076 if (dst
.r_type
== R_IHCONST
) {
3077 /* Add in the value which was stored in the symbol index */
3078 /* See above comment */
3079 cache_ptr
->addend
+= dst
.r_symndx
;
3080 /* Throw away the bogus symbol pointer */
3081 cache_ptr
->sym_ptr_ptr
= 0;
3083 cache_ptr
->howto
= howto_table
+ dst
.r_type
;
3086 cache_ptr
->howto
= howto_table
+ dst
.r_type
;
3089 cache_ptr
->howto
= howto_table
+ dst
.r_type
;
3092 cache_ptr
->howto
= howto_table
+ dst
.r_type
- R_RELBYTE
;
3095 if (dst
.r_type
>= R_PCR16L
&& dst
.r_type
<= R_VRT32
) {
3096 cache_ptr
->howto
= howto_table
+ dst
.r_type
- R_PCR16L
;
3097 cache_ptr
->addend
+= dst
.r_offset
<< 16;
3108 asect
->relocation
= reloc_cache
;
3113 /* This is stupid. This function should be a boolean predicate */
3115 coff_canonicalize_reloc(abfd
, section
, relptr
, symbols
)
3121 arelent
*tblptr
= section
->relocation
;
3122 unsigned int count
= 0;
3123 if (!(tblptr
|| coff_slurp_reloc_table(abfd
, section
, symbols
)))
3125 tblptr
= section
->relocation
;
3129 for (; count
++ < section
->reloc_count
;)
3130 *relptr
++ = tblptr
++;
3134 return section
->reloc_count
;
3137 #ifndef NO_COFF_SYMBOLS
3140 provided a BFD, a section and an offset into the section, calculate and
3141 return the name of the source file and the line nearest to the wanted
3146 DEFUN(coff_find_nearest_line
,(abfd
,
3154 asection
*section AND
3155 asymbol
**ignore_symbols AND
3157 CONST
char **filename_ptr AND
3158 CONST
char **functionname_ptr AND
3159 unsigned int *line_ptr
)
3161 static bfd
*cache_abfd
;
3162 static asection
*cache_section
;
3163 static bfd_vma cache_offset
;
3164 static unsigned int cache_i
;
3165 static alent
*cache_l
;
3168 coff_data_type
*cof
= coff_data(abfd
);
3169 /* Run through the raw syments if available */
3170 combined_entry_type
*p
;
3172 unsigned int line_base
= 0;
3176 *functionname_ptr
= 0;
3179 /* Don't try and find line numbers in a non coff file */
3180 if (abfd
->xvec
->flavour
!= bfd_target_coff_flavour
)
3186 p
= cof
->raw_syments
;
3188 for (i
= 0; i
< cof
->raw_syment_count
; i
++) {
3189 if (p
->u
.syment
.n_sclass
== C_FILE
) {
3190 /* File name has been moved into symbol */
3191 *filename_ptr
= (char *) p
->u
.syment
._n
._n_n
._n_offset
;
3194 p
+= 1 + p
->u
.syment
.n_numaux
;
3196 /* Now wander though the raw linenumbers of the section */
3198 If this is the same BFD as we were previously called with and this is
3199 the same section, and the offset we want is further down then we can
3200 prime the lookup loop
3202 if (abfd
== cache_abfd
&&
3203 section
== cache_section
&&
3204 offset
>= cache_offset
) {
3210 l
= section
->lineno
;
3213 for (; i
< section
->lineno_count
; i
++) {
3214 if (l
->line_number
== 0) {
3215 /* Get the symbol this line number points at */
3216 coff_symbol_type
*coff
= (coff_symbol_type
*) (l
->u
.sym
);
3217 *functionname_ptr
= coff
->symbol
.name
;
3219 combined_entry_type
*s
= coff
->native
;
3220 s
= s
+ 1 + s
->u
.syment
.n_numaux
;
3222 S should now point to the .bf of the function
3224 if (s
->u
.syment
.n_numaux
) {
3226 The linenumber is stored in the auxent
3228 union internal_auxent
*a
= &((s
+ 1)->u
.auxent
);
3229 line_base
= a
->x_sym
.x_misc
.x_lnsz
.x_lnno
;
3234 if (l
->u
.offset
> offset
)
3236 *line_ptr
= l
->line_number
+ line_base
+ 1;
3242 cache_section
= section
;
3243 cache_offset
= offset
;
3252 coff_sym_filepos(abfd
)
3255 return obj_sym_filepos(abfd
);
3259 #endif /* NO_COFF_SYMBOLS */
3263 DEFUN(coff_sizeof_headers
,(abfd
, reloc
),
3269 if (reloc
== false) {
3270 size
= FILHSZ
+ AOUTSZ
;
3276 size
+= abfd
->section_count
* SCNHSZ
;
3281 #define coff_core_file_failing_command _bfd_dummy_core_file_failing_command
3282 #define coff_core_file_failing_signal _bfd_dummy_core_file_failing_signal
3283 #define coff_core_file_matches_executable_p _bfd_dummy_core_file_matches_executable_p
3284 #define coff_slurp_armap bfd_slurp_coff_armap
3285 #define coff_slurp_extended_name_table _bfd_slurp_extended_name_table
3286 #define coff_truncate_arname bfd_dont_truncate_arname
3287 #define coff_openr_next_archived_file bfd_generic_openr_next_archived_file
3288 #define coff_generic_stat_arch_elt bfd_generic_stat_arch_elt
3289 #define coff_get_section_contents bfd_generic_get_section_contents
3290 #define coff_close_and_cleanup bfd_generic_close_and_cleanup
3292 #define coff_bfd_debug_info_start bfd_void
3293 #define coff_bfd_debug_info_end bfd_void
3294 #define coff_bfd_debug_info_accumulate (PROTO(void,(*),(bfd*, struct sec *))) bfd_void