Don't use prototypes for vfprintf_filtered(). Someday we'll get prototypes of
[external/binutils.git] / bfd / coff-code.h
1 /* Support for Intel 960 COFF and Motorola 88k BCS COFF (and maybe others) */
2
3 /* Copyright (C) 1990, 1991 Free Software Foundation, Inc.
4
5 This file is part of BFD, the Binary File Diddler.
6
7 BFD is free software; you can redistribute it and/or modify it under the
8    terms of the GNU General Public License as published by the Free Software
9    Foundation; either version 1, or (at your option) any later version.
10
11 BFD is distributed in the hope that it will be useful, but WITHOUT ANY
12    WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
13    FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more
14    details.
15
16 You should have received a copy of the GNU General Public License along with
17    BFD; see the file COPYING.  If not, write to the Free Software Foundation,
18    675 Mass Ave, Cambridge, MA 02139, USA.
19 */
20
21 /* $Id$ */
22 /* Most of this hacked by Steve Chamberlain, steve@cygnus.com */
23
24 #include "archures.h"           /* Machine architectures and types */
25
26 /* SUPPRESS 558 */
27 /* SUPPRESS 590 */
28 /* SUPPRESS 529 */
29 /* SUPPRESS 530 */
30
31 /* Align an address upward to a boundary, expressed as a number of bytes.
32    E.g. align to an 8-byte boundary with argument of 8.  */
33 #define ALIGN(this, boundary) \
34   ((( (this) + ((boundary) -1)) & (~((boundary)-1))))
35
36 /* Align an address upward to a power of two.  Argument is the power
37    of two, e.g. 8-byte alignment uses argument of 3 (8 == 2^3).  */
38 #define i960_align(addr, align) \
39         ( ((addr) + ((1<<(align))-1)) & (-1 << (align)))
40
41 #define sp(x) bfd_h_put_x(abfd, x, &x)
42
43 #ifndef I960
44 #define GDB_EXPORT static
45 #else
46 #define GDB_EXPORT  /* nothing */
47 #endif
48
49 PROTO(static void,force_indices_file_symbol_relative,(bfd *abfd,
50                                                       struct internal_syment *symtab));
51
52 \f
53 /* void warning(); */
54 extern asection abs_section;
55
56 static int
57 DEFUN(get_index,(symbol),
58       asymbol        *symbol)
59 {
60     return (int) symbol->value;
61 }
62
63 static void
64 DEFUN(set_index,(symbol, idx),
65       asymbol        *symbol AND
66       unsigned int    idx)
67 {
68     symbol->value = idx;
69 }
70
71
72
73
74
75 /* All the swapping routines:
76 */
77
78
79 GDB_EXPORT
80 void
81 DEFUN(bfd_swap_reloc_in,(abfd, reloc_src, reloc_dst),
82       bfd            *abfd AND
83       RELOC *reloc_src AND
84       struct internal_reloc *reloc_dst)
85 {
86   reloc_dst->r_vaddr = bfd_h_getlong(abfd, reloc_src->r_vaddr);
87   reloc_dst->r_symndx = bfd_h_getlong(abfd, reloc_src->r_symndx);
88   reloc_dst->r_type = bfd_h_getshort(abfd, reloc_src->r_type);
89 #if M88
90   reloc_dst->r_offset = bfd_h_getshort(abfd, reloc_src->r_offset);
91 #endif
92 }
93
94 GDB_EXPORT
95  void
96 DEFUN(bfd_swap_reloc_out,(abfd, reloc_src, reloc_dst),
97       bfd            *abfd AND
98       struct internal_reloc *reloc_src AND
99       struct external_reloc *reloc_dst)
100 {
101   bfd_h_putlong(abfd, reloc_src->r_vaddr, reloc_dst->r_vaddr);
102   bfd_h_putlong(abfd, reloc_src->r_symndx, reloc_dst->r_symndx);
103   bfd_h_putshort(abfd, reloc_src->r_type, reloc_dst->r_type);
104 #if M88
105   bfd_h_putshort(abfd, reloc_src->r_offset, reloc_dst->r_offset);
106 #endif
107
108 }
109
110 GDB_EXPORT  void 
111 DEFUN(bfd_swap_filehdr_in,(abfd, filehdr_src, filehdr_dst),
112       bfd            *abfd AND
113       FILHDR         *filehdr_src AND
114       struct internal_filehdr *filehdr_dst)
115 {
116   filehdr_dst->f_magic = bfd_h_get_x(abfd, filehdr_src->f_magic);
117   filehdr_dst->f_nscns = bfd_h_get_x(abfd,filehdr_src-> f_nscns);
118   filehdr_dst->f_timdat = bfd_h_get_x(abfd,filehdr_src-> f_timdat);
119   filehdr_dst->f_symptr = bfd_h_get_x(abfd,filehdr_src-> f_symptr);
120   filehdr_dst->f_nsyms = bfd_h_get_x(abfd,filehdr_src-> f_nsyms);
121   filehdr_dst->f_opthdr = bfd_h_get_x(abfd,filehdr_src-> f_opthdr);
122   filehdr_dst->f_flags = bfd_h_get_x(abfd,filehdr_src-> f_flags);
123 }
124
125 GDB_EXPORT  void 
126 DEFUN(bfd_swap_filehdr_out,(abfd, filehdr_in, filehdr_out),
127       bfd            *abfd AND
128       struct internal_filehdr *filehdr_in AND
129       FILHDR         *filehdr_out)
130 {
131   bfd_h_put_x(abfd, filehdr_in->f_magic, filehdr_out->f_magic);
132   bfd_h_put_x(abfd, filehdr_in->f_nscns, filehdr_out->f_nscns);
133   bfd_h_put_x(abfd, filehdr_in->f_timdat, filehdr_out->f_timdat);
134   bfd_h_put_x(abfd, filehdr_in->f_symptr, filehdr_out->f_symptr);
135   bfd_h_put_x(abfd, filehdr_in->f_nsyms, filehdr_out->f_nsyms);
136   bfd_h_put_x(abfd, filehdr_in->f_opthdr, filehdr_out->f_opthdr);
137   bfd_h_put_x(abfd, filehdr_in->f_flags, filehdr_out->f_flags);
138 }
139
140
141 GDB_EXPORT 
142 void 
143 DEFUN(bfd_coff_swap_sym_in,(abfd, ext, in),
144       bfd            *abfd AND
145       SYMENT *ext AND
146       struct internal_syment      *in)
147 {
148   if( ext->e.e_name[0] == 0) {
149     in->_n._n_n._n_zeroes = 0;
150     in->_n._n_n._n_offset = bfd_h_getlong(abfd, ext->e.e.e_offset);
151   }
152   else {
153     memcpy(in->_n._n_name, ext->e.e_name, SYMNMLEN);
154   }
155   in->n_value = bfd_h_get_x(abfd, ext->e_value);
156   in->n_scnum = bfd_h_get_x(abfd, ext->e_scnum);
157   in->n_type = bfd_h_get_x(abfd, ext->e_type);
158   in->n_sclass = bfd_h_get_x(abfd, ext->e_sclass);
159   in->n_numaux = bfd_h_get_x(abfd, ext->e_numaux);
160 }
161
162 GDB_EXPORT void 
163 DEFUN(bfd_coff_swap_sym_out,(abfd,in,  ext),
164       bfd            *abfd AND
165       struct internal_syment      *in AND
166       SYMENT *ext)
167 {
168   if(in->_n._n_name[0] == 0) {
169     bfd_h_putlong(abfd, 0, ext->e.e.e_zeroes);
170     bfd_h_putlong(abfd, in->_n._n_n._n_offset,  ext->e.e.e_offset);
171   }
172   else {
173     memcpy(ext->e.e_name, in->_n._n_name, SYMNMLEN);
174   }
175   bfd_h_put_x(abfd,  in->n_value , ext->e_value);
176   bfd_h_put_x(abfd,  in->n_scnum , ext->e_scnum);
177   bfd_h_put_x(abfd,  in->n_type , ext->e_type);
178   bfd_h_put_x(abfd,  in->n_sclass , ext->e_sclass);
179   bfd_h_put_x(abfd,  in->n_numaux , ext->e_numaux);
180 }
181
182 GDB_EXPORT void
183 DEFUN(bfd_coff_swap_aux_in,(abfd, ext, type, class, in),
184       bfd            *abfd AND
185       AUXENT    *ext AND
186       int             type AND
187       int             class AND
188       union internal_auxent  *in)
189 {
190   switch (class) {
191   case C_FILE:
192     if (ext->x_file.x_fname[0] == 0) {
193       in->x_file.x_n.x_zeroes = 0;
194       in->x_file.x_n.x_offset  = bfd_h_getlong(abfd, ext->x_file.x_n.x_offset);
195     }
196
197     break;
198   case C_STAT:
199 #ifdef C_LEAFSTAT
200   case C_LEAFSTAT:
201 #endif
202   case C_HIDDEN:
203     if (type == T_NULL) {
204       in->x_scn.x_scnlen = bfd_h_get_x(abfd, ext->x_scn.x_scnlen);
205       in->x_scn.x_nreloc = bfd_h_get_x(abfd, ext->x_scn.x_nreloc);
206       in->x_scn.x_nlinno = bfd_h_get_x(abfd, ext->x_scn.x_nlinno);
207       break;
208     }
209   default:
210     in->x_sym.x_tagndx = bfd_h_get_x(abfd, ext->x_sym.x_tagndx);
211     in->x_sym.x_tvndx = bfd_h_get_x(abfd, ext->x_sym.x_tvndx);
212
213     if (ISARY(type) || class == C_BLOCK) {
214       in->x_sym.x_fcnary.x_ary.x_dimen[0] = bfd_h_get_x(abfd, ext->x_sym.x_fcnary.x_ary.x_dimen[0]);
215       in->x_sym.x_fcnary.x_ary.x_dimen[1] = bfd_h_get_x(abfd, ext->x_sym.x_fcnary.x_ary.x_dimen[1]);
216       in->x_sym.x_fcnary.x_ary.x_dimen[2] = bfd_h_get_x(abfd, ext->x_sym.x_fcnary.x_ary.x_dimen[2]);
217       in->x_sym.x_fcnary.x_ary.x_dimen[3] = bfd_h_get_x(abfd, ext->x_sym.x_fcnary.x_ary.x_dimen[3]);
218     }
219     else {
220       in->x_sym.x_fcnary.x_fcn.x_lnnoptr = bfd_h_get_x(abfd, ext->x_sym.x_fcnary.x_fcn.x_lnnoptr);
221       in->x_sym.x_fcnary.x_fcn.x_endndx = bfd_h_get_x(abfd, ext->x_sym.x_fcnary.x_fcn.x_endndx);
222     }
223     if (ISFCN(type)) {
224       in->x_sym.x_misc.x_fsize = bfd_h_get_x(abfd, ext->x_sym.x_misc.x_fsize);
225     }
226     else {
227       in->x_sym.x_misc.x_lnsz.x_lnno = bfd_h_get_x(abfd, ext->x_sym.x_misc.x_lnsz.x_lnno);
228       in->x_sym.x_misc.x_lnsz.x_size = bfd_h_get_x(abfd, ext->x_sym.x_misc.x_lnsz.x_size);
229     }
230   }
231 }
232
233 GDB_EXPORT void
234 DEFUN(bfd_coff_swap_aux_out,(abfd, in, type, class, ext),
235   bfd   *abfd AND
236   union internal_auxent *in AND
237   int    type AND
238   int    class AND
239   AUXENT *ext)
240 {
241   switch (class) {
242   case C_FILE:
243     if (in->x_file.x_fname[0] == 0) {
244       bfd_h_put_x(abfd, 0, ext->x_file.x_n.x_zeroes );
245       bfd_h_put_x(abfd, in->x_file.x_n.x_offset, ext->x_file.x_n.x_offset);
246     }
247
248     break;
249   case C_STAT:
250 #ifdef C_LEAFSTAT
251   case C_LEAFSTAT:
252 #endif
253   case C_HIDDEN:
254     if (type == T_NULL) {
255       bfd_h_put_x(abfd, in->x_scn.x_scnlen, ext->x_scn.x_scnlen);
256       bfd_h_put_x(abfd, in->x_scn.x_nreloc, ext->x_scn.x_nreloc);
257       bfd_h_put_x(abfd, in->x_scn.x_nlinno, ext->x_scn.x_nlinno);
258       break;
259     }
260   default:
261     bfd_h_put_x(abfd, in->x_sym.x_tagndx, ext->x_sym.x_tagndx);
262     bfd_h_put_x(abfd, in->x_sym.x_tvndx , ext->x_sym.x_tvndx);
263
264     if (ISARY(type) || class == C_BLOCK) {
265       bfd_h_put_x(abfd, in->x_sym.x_fcnary.x_ary.x_dimen[0],ext->x_sym.x_fcnary.x_ary.x_dimen[0]);
266       bfd_h_put_x(abfd, in->x_sym.x_fcnary.x_ary.x_dimen[1],ext->x_sym.x_fcnary.x_ary.x_dimen[1]);
267       bfd_h_put_x(abfd, in->x_sym.x_fcnary.x_ary.x_dimen[2],ext->x_sym.x_fcnary.x_ary.x_dimen[2]);
268       bfd_h_put_x(abfd, in->x_sym.x_fcnary.x_ary.x_dimen[3],ext->x_sym.x_fcnary.x_ary.x_dimen[3]);
269     }
270     else {
271       bfd_h_put_x(abfd, in->x_sym.x_fcnary.x_fcn.x_lnnoptr, ext->x_sym.x_fcnary.x_fcn.x_lnnoptr);
272       bfd_h_put_x(abfd, in->x_sym.x_fcnary.x_fcn.x_endndx, ext->x_sym.x_fcnary.x_fcn.x_endndx);
273     }
274     if (ISFCN(type)) {
275       bfd_h_put_x(abfd, in->x_sym.x_misc.x_fsize, ext->x_sym.x_misc.x_fsize);
276     }
277     else {
278       bfd_h_put_x(abfd, in->x_sym.x_misc.x_lnsz.x_lnno, ext->x_sym.x_misc.x_lnsz.x_lnno);
279       bfd_h_put_x(abfd, in->x_sym.x_misc.x_lnsz.x_size, ext->x_sym.x_misc.x_lnsz.x_size);
280     }
281   }
282 }
283
284 GDB_EXPORT void
285 DEFUN(bfd_coff_swap_lineno_in,(abfd, ext, in),
286       bfd            *abfd AND
287       LINENO *ext AND
288       struct internal_lineno      *in)
289 {
290     in->l_addr.l_symndx = bfd_h_get_x(abfd, ext->l_addr.l_symndx);
291     in->l_lnno = bfd_h_get_x(abfd, ext->l_lnno);
292 }
293
294 GDB_EXPORT void
295 DEFUN(bfd_coff_swap_lineno_out,(abfd, in, ext),
296       bfd            *abfd AND
297       struct internal_lineno      *in AND
298       struct external_lineno *ext)
299 {
300   bfd_h_put_x(abfd, in->l_addr.l_symndx, ext->l_addr.l_symndx);
301   bfd_h_put_x(abfd, in->l_lnno, ext->l_lnno);
302 }
303
304
305
306
307 GDB_EXPORT void 
308 DEFUN(bfd_swap_aouthdr_in,(abfd, aouthdr_ext, aouthdr_int),
309       bfd            *abfd AND
310       AOUTHDR        *aouthdr_ext AND
311       struct internal_aouthdr *aouthdr_int)
312 {
313   aouthdr_int->magic = bfd_h_get_x(abfd, aouthdr_ext->magic);
314   aouthdr_int->vstamp = bfd_h_get_x(abfd, aouthdr_ext->vstamp);
315   aouthdr_int->tsize = bfd_h_get_x(abfd, aouthdr_ext->tsize);
316   aouthdr_int->dsize = bfd_h_get_x(abfd, aouthdr_ext->dsize);
317   aouthdr_int->bsize = bfd_h_get_x(abfd, aouthdr_ext->bsize);
318   aouthdr_int->entry = bfd_h_get_x(abfd, aouthdr_ext->entry);
319   aouthdr_int->text_start = bfd_h_get_x(abfd, aouthdr_ext->text_start);
320   aouthdr_int->data_start = bfd_h_get_x(abfd, aouthdr_ext->data_start);
321 #ifdef I960
322   aouthdr_int->tagentries = bfd_h_get_x(abfd, aouthdr_ext->tagentries);
323 #endif
324 }
325
326 GDB_EXPORT void 
327 DEFUN(bfd_swap_aouthdr_out,(abfd, aouthdr_in, aouthdr_out),
328       bfd            *abfd AND
329       struct internal_aouthdr *aouthdr_in AND
330       AOUTHDR        *aouthdr_out)
331 {
332   bfd_h_put_x(abfd, aouthdr_in->magic, aouthdr_out->magic);
333   bfd_h_put_x(abfd, aouthdr_in->vstamp, aouthdr_out->vstamp);
334   bfd_h_put_x(abfd, aouthdr_in->tsize, aouthdr_out->tsize);
335   bfd_h_put_x(abfd, aouthdr_in->dsize, aouthdr_out->dsize);
336   bfd_h_put_x(abfd, aouthdr_in->bsize, aouthdr_out->bsize);
337   bfd_h_put_x(abfd, aouthdr_in->entry, aouthdr_out->entry);
338   bfd_h_put_x(abfd, aouthdr_in->text_start, aouthdr_out->text_start);
339   bfd_h_put_x(abfd, aouthdr_in->data_start, aouthdr_out->data_start);
340 #ifdef I960
341   bfd_h_put_x(abfd, aouthdr_in->tagentries, aouthdr_out->tagentries);
342 #endif
343 }
344
345 GDB_EXPORT void 
346 DEFUN(bfd_coff_swap_scnhdr_in,(abfd, scnhdr_ext, scnhdr_int),
347       bfd            *abfd AND
348       SCNHDR         *scnhdr_ext AND
349       struct internal_scnhdr *scnhdr_int)
350 {
351   memcpy(scnhdr_int->s_name, scnhdr_ext->s_name, sizeof(scnhdr_int->s_name));
352   scnhdr_int->s_vaddr = bfd_h_get_x(abfd, scnhdr_ext->s_vaddr);
353   scnhdr_int->s_paddr = bfd_h_get_x(abfd, scnhdr_ext->s_paddr);
354   scnhdr_int->s_size = bfd_h_get_x(abfd, scnhdr_ext->s_size);
355   scnhdr_int->s_scnptr = bfd_h_get_x(abfd, scnhdr_ext->s_scnptr);
356   scnhdr_int->s_relptr = bfd_h_get_x(abfd, scnhdr_ext->s_relptr);
357   scnhdr_int->s_lnnoptr = bfd_h_get_x(abfd, scnhdr_ext->s_lnnoptr);
358   scnhdr_int->s_nreloc = bfd_h_get_x(abfd, scnhdr_ext->s_nreloc);
359   scnhdr_int->s_nlnno = bfd_h_get_x(abfd, scnhdr_ext->s_nlnno);
360   scnhdr_int->s_flags = bfd_h_get_x(abfd, scnhdr_ext->s_flags);
361 #ifdef I960
362   scnhdr_int->s_align = bfd_h_get_x(abfd, scnhdr_ext->s_align);
363 #endif
364 }
365
366 static void 
367 DEFUN(swap_scnhdr_out,(abfd, scnhdr_int, scnhdr_ext),
368       bfd            *abfd AND
369       struct internal_scnhdr *scnhdr_int AND
370       SCNHDR         *scnhdr_ext)
371 {
372   memcpy(scnhdr_ext->s_name, scnhdr_int->s_name, sizeof(scnhdr_int->s_name));
373   bfd_h_put_x(abfd, scnhdr_int->s_vaddr, scnhdr_ext->s_vaddr);
374   bfd_h_put_x(abfd, scnhdr_int->s_paddr, scnhdr_ext->s_paddr);
375   bfd_h_put_x(abfd, scnhdr_int->s_size, scnhdr_ext->s_size);
376   bfd_h_put_x(abfd, scnhdr_int->s_scnptr, scnhdr_ext->s_scnptr);
377   bfd_h_put_x(abfd, scnhdr_int->s_relptr, scnhdr_ext->s_relptr);
378   bfd_h_put_x(abfd, scnhdr_int->s_lnnoptr, scnhdr_ext->s_lnnoptr);
379   bfd_h_put_x(abfd, scnhdr_int->s_nreloc, scnhdr_ext->s_nreloc);
380   bfd_h_put_x(abfd, scnhdr_int->s_nlnno, scnhdr_ext->s_nlnno);
381   bfd_h_put_x(abfd, scnhdr_int->s_flags, scnhdr_ext->s_flags);
382 #ifdef I960
383   bfd_h_put_x(abfd, scnhdr_int->s_align, scnhdr_ext->s_align);
384 #endif
385 }
386
387 /*
388    initialize a section structure with information peculiar to this
389    particular implementation of coff
390 */
391
392 static          boolean
393 DEFUN(coff_new_section_hook,(abfd_ignore, section_ignore),
394       bfd            *abfd_ignore AND
395       asection       *section_ignore)
396 {
397 #ifdef MC88MAGIC
398   /* FIXME, shouldn't this ifdef be on something that says we are
399      actually COMPILING FOR an 88K coff file, rather than simply
400      knowing its magic number? */
401   /* Align to at least 16 bytes */
402   section_ignore->alignment_power = 4;
403 #endif
404 #if M68
405   section_ignore->alignment_power = 3;
406 #endif
407   return true;
408 }
409
410 /* Take a section header read from a coff file (in HOST byte order),
411    and make a BFD "section" out of it.  */
412 static          boolean
413 DEFUN(make_a_section_from_file,(abfd, hdr),
414       bfd            *abfd AND
415       struct internal_scnhdr  *hdr)
416 {
417     asection       *return_section;
418
419     {
420         /* Assorted wastage to null-terminate the name, thanks AT&T! */
421         char *name = bfd_alloc(abfd, sizeof (hdr->s_name)+1);
422         if (name == NULL) {
423             bfd_error = no_memory;
424             return false;
425         }
426         strncpy(name, (char *) &hdr->s_name[0], sizeof (hdr->s_name));
427         name[sizeof (hdr->s_name)] = 0;
428
429         return_section = bfd_make_section(abfd, name);
430     }
431
432     /* s_paddr is presumed to be = to s_vaddr */
433 #define assign(to, from) return_section->to = hdr->from
434     assign(vma, s_vaddr);
435     /* assign (vma, s_vaddr); */
436     assign(size, s_size);
437     assign(filepos, s_scnptr);
438     assign(rel_filepos, s_relptr);
439     assign(reloc_count, s_nreloc);
440 #ifdef I960
441     {
442         /* FIXME, use a temp var rather than alignment_power */
443         assign(alignment_power, s_align);
444         {
445             unsigned int    i;
446             for (i = 0; i < 32; i++) {
447                 if ((1 << i) >= (int) (return_section->alignment_power)) {
448                     return_section->alignment_power = i;
449                     break;
450                 }
451             }
452         }
453     }
454 #endif
455     assign(line_filepos, s_lnnoptr);
456     /*
457        return_section->linesize =   hdr->s_nlnno * sizeof (struct lineno);
458     */
459
460 #undef assign
461     return_section->lineno_count = hdr->s_nlnno;
462     return_section->userdata = NULL;
463     return_section->next = (asection *) NULL;
464     return_section->flags = 0;
465     if ((hdr->s_flags & STYP_TEXT) || (hdr->s_flags & STYP_DATA))
466         return_section->flags = (SEC_LOAD | SEC_ALLOC);
467     else if (hdr->s_flags & STYP_BSS)
468         return_section->flags = SEC_ALLOC;
469
470     if (hdr->s_nreloc != 0)
471         return_section->flags |= SEC_RELOC;
472     if (hdr->s_scnptr != 0)
473         return_section->flags |= SEC_HAS_CONTENTS;
474     return true;
475 }
476 static          boolean
477 DEFUN(coff_mkobject,(abfd),
478       bfd            *abfd)
479 {
480   set_tdata (abfd, bfd_zalloc (abfd,sizeof(coff_data_type)));
481   if (coff_data(abfd) == 0) {
482     bfd_error = no_memory;
483     return false;
484   }
485   coff_data(abfd)->relocbase = 0;
486   return true;
487 }
488
489 static
490 bfd_target     *
491 DEFUN(coff_real_object_p,(abfd, nscns, internal_f, internal_a),
492     bfd            *abfd AND
493     unsigned        nscns AND
494   struct internal_filehdr *internal_f AND
495   struct internal_aouthdr *internal_a)
496 {
497   coff_data_type *coff;
498
499   size_t          readsize;     /* length of file_info */
500   SCNHDR *external_sections;
501   
502   /* Build a play area */
503   if (coff_mkobject(abfd) != true)
504     return 0;
505   coff = coff_data(abfd);
506   
507   
508   external_sections = (SCNHDR *)bfd_alloc(abfd, readsize = (nscns * SCNHSZ));
509   if (bfd_read((PTR)external_sections, 1, readsize, abfd) != readsize) {
510     goto fail;
511   }
512   
513   
514   
515   /* Now copy data as required; construct all asections etc */
516   coff->symbol_index_slew = 0;
517   coff->relocbase =0;
518   coff->raw_syment_count = 0;
519   coff->raw_linenos = 0;
520   coff->raw_syments = 0;
521   coff->sym_filepos =0;
522   coff->flags = internal_f->f_flags;
523   if (nscns != 0) {
524     unsigned int    i;
525     for (i = 0; i < nscns; i++) {
526       struct internal_scnhdr tmp;
527       bfd_coff_swap_scnhdr_in(abfd, external_sections + i, &tmp);
528       make_a_section_from_file(abfd,&tmp);
529     }
530   }
531   /* Determine the machine architecture and type.  */
532   abfd->obj_machine = 0;
533   switch (internal_f->f_magic) {
534 #ifdef MIPS
535 case  MIPS_MAGIC_1:
536 case  MIPS_MAGIC_2:
537 case  MIPS_MAGIC_3:
538     abfd->obj_arch = bfd_arch_mips;
539     abfd->obj_machine = 0;
540     break;
541 #endif
542
543 #ifdef MC68MAGIC
544   case MC68MAGIC:
545   case M68MAGIC:
546     abfd->obj_arch = bfd_arch_m68k;
547     abfd->obj_machine = 68020;
548     break;
549 #endif
550 #ifdef MC88MAGIC
551   case MC88MAGIC:
552   case MC88DMAGIC:
553   case MC88OMAGIC:
554     abfd->obj_arch = bfd_arch_m88k;
555     abfd->obj_machine = 88100;
556     break;
557 #endif
558 #ifdef I960
559 #ifdef I960ROMAGIC
560   case I960ROMAGIC:
561   case I960RWMAGIC:
562     abfd->obj_arch = bfd_arch_i960;
563     switch (F_I960TYPE & internal_f->f_flags) 
564         {
565         default:
566         case F_I960CORE:
567           abfd->obj_machine = bfd_mach_i960_core;
568           break;
569         case F_I960KB:
570           abfd->obj_machine = bfd_mach_i960_kb_sb;
571           break;
572         case F_I960MC:
573           abfd->obj_machine = bfd_mach_i960_mc;
574           break;
575         case F_I960XA:
576           abfd->obj_machine = bfd_mach_i960_xa;
577           break;
578         case F_I960CA:
579           abfd->obj_machine = bfd_mach_i960_ca;
580           break;
581         case F_I960KA:
582           abfd->obj_machine = bfd_mach_i960_ka_sa;
583           break;
584           
585         }
586     break;
587 #endif
588 #endif
589     
590   default:                      /* Unreadable input file type */
591     abfd->obj_arch = bfd_arch_obscure;
592     break;
593   }
594   
595   if (!(internal_f->f_flags & F_RELFLG))
596     abfd->flags |= HAS_RELOC;
597   if ((internal_f->f_flags & F_EXEC))
598     abfd->flags |= EXEC_P;
599   if (!(internal_f->f_flags & F_LNNO))
600     abfd->flags |= HAS_LINENO;
601   if (!(internal_f->f_flags & F_LSYMS))
602     abfd->flags |= HAS_LOCALS;
603   
604   
605   bfd_get_symcount(abfd) = internal_f->f_nsyms;
606   if (internal_f->f_nsyms)
607     abfd->flags |= HAS_SYMS;
608   
609   coff->sym_filepos = internal_f->f_symptr;
610   
611   
612   
613   coff->symbols = (coff_symbol_type *) NULL;
614   bfd_get_start_address(abfd) = internal_f->f_opthdr ? internal_a->entry : 0;
615   
616   return abfd->xvec;
617  fail:
618   bfd_release(abfd, coff);
619   return (bfd_target *)NULL;
620 }
621
622 static bfd_target *
623 DEFUN(coff_object_p,(abfd),
624       bfd            *abfd)
625   {
626     int   nscns;
627     FILHDR filehdr;
628     AOUTHDR opthdr;
629     struct internal_filehdr internal_f;
630     struct internal_aouthdr internal_a;
631     
632     bfd_error = system_call_error;
633     
634     /* figure out how much to read */
635     if (bfd_read((PTR) &filehdr, 1, FILHSZ, abfd) != FILHSZ)
636       return 0;
637     
638     bfd_swap_filehdr_in(abfd, &filehdr, &internal_f);
639     
640     if (BADMAG(internal_f)) {
641       bfd_error = wrong_format;
642       return 0;
643     }
644     nscns =internal_f.f_nscns;
645     
646     if (internal_f.f_opthdr) {
647       if (bfd_read((PTR) &opthdr, 1,AOUTSZ, abfd) != AOUTSZ) {
648         return 0;
649       }
650       bfd_swap_aouthdr_in(abfd, &opthdr, &internal_a);
651     }
652     
653     /* Seek past the opt hdr stuff */
654     bfd_seek(abfd, internal_f.f_opthdr + FILHSZ, SEEK_SET);
655     
656     /* if the optional header is NULL or not the correct size then
657       quit; the only difference I can see between m88k dgux headers (MC88DMAGIC)
658         and Intel 960 readwrite headers (I960WRMAGIC) is that the
659           optional header is of a different size.
660
661         But the mips keeps extra stuff in it's opthdr, so dont check
662         when doing that
663             */
664     
665 #ifndef MIPS    
666     if (internal_f.f_opthdr != 0 && AOUTSZ != internal_f.f_opthdr)
667       return (bfd_target *)NULL;
668 #endif
669     
670     return coff_real_object_p(abfd, nscns, &internal_f, &internal_a);
671   }
672
673
674
675
676 /* 
677 Takes a bfd and a symbol, returns a pointer to the coff specific area
678 of the symbol if there is one.
679 */
680 static coff_symbol_type *
681 DEFUN(coff_symbol_from,(abfd, symbol),
682       bfd            *abfd AND
683       asymbol        *symbol)
684 {
685   if (symbol->the_bfd->xvec->flavour != bfd_target_coff_flavour_enum) 
686     return (coff_symbol_type *)NULL;
687
688   if (symbol->the_bfd->tdata == (PTR)NULL)
689     return (coff_symbol_type *)NULL;
690
691   return  (coff_symbol_type *) symbol;
692 }
693
694
695
696
697
698
699
700 static void 
701 DEFUN(coff_count_linenumbers,(abfd),
702       bfd            *abfd)
703 {
704     unsigned int    limit = bfd_get_symcount(abfd);
705     unsigned int    i;
706     asymbol       **p;
707     {
708         asection       *s = abfd->sections->output_section;
709         while (s) {
710             BFD_ASSERT(s->lineno_count == 0);
711             s = s->next;
712         }
713     }
714
715
716     for (p = abfd->outsymbols, i = 0; i < limit; i++, p++) {
717         asymbol        *q_maybe = *p;
718         if (q_maybe->the_bfd->xvec->flavour == bfd_target_coff_flavour_enum) {
719             coff_symbol_type *q = coffsymbol(q_maybe);
720             if (q->lineno) {
721                 /*
722                    This symbol has a linenumber, increment the owning
723                    section's linenumber count
724                 */
725                 alent          *l = q->lineno;
726                 q->symbol.section->output_section->lineno_count++;
727                 l++;
728                 while (l->line_number) {
729                     q->symbol.section->output_section->lineno_count++;
730                     l++;
731                 }
732             }
733         }
734     }
735 }
736
737 /*
738  This function returns true if the supplied SYMENT has an AUXENT with
739  a tagndx field which should be relocated.
740
741  The coff book says that all auxents have this and should be moved,
742  but all the actual implementations I've looked at do this ..
743  (sac@cygnus.com)
744
745 */
746 static boolean
747 DEFUN(uses_x_sym_x_tagndx_p,(abfd, native),
748       bfd *abfd AND
749       struct internal_syment *native)
750 {
751     if (BTYPE(native->n_type) == T_STRUCT) return true;
752     if (BTYPE(native->n_type) == T_UNION)  return true;
753     if (BTYPE(native->n_type) == T_ENUM)   return true;
754     return false;
755 }
756
757
758 /* 
759 This procedure runs through the native entries in a coff symbol table
760 and links up all the elements which should point to one another, in
761 particular these are:
762
763 strtag, entag and untags have an auxent endindex which points to the
764 first syment after the .eos. This is simple to do, we just keep a
765 pointer to the symbol with the most recent pending strtag and patch it
766 when we see the eos. This works since coff structs are never nested.
767
768 ISFCN type entries have an endindex which points to the next static or
769 extern in the table, thereby skipping the function contents.
770 The coff book says that an ISFCN's tagindex
771 points to the first .bf for the function, so far I havn't seen it
772 used. We do this using the same mechanism as strtags.
773
774 Each file entry has a value which points to the next file entry,
775 the last file entry points to the first extern symbol in the table
776 which is not an ISFCN.
777
778 Each .bb entry points to the matching .eb entry, but these are nested
779 so we keep a stack of them.
780
781 The tagndx of .eos items points to the strtag attached to them, this
782 is simply the last_tagndx again. 
783
784 The tagndx of items with type strtag point to the defining struct.
785 This bit is complicated; We know that a struct ref and def must be
786 within the same file, so all the natives will be in the same vector.
787 This means that we can subtracts two pointers and get the index
788 differences between to items, used to work out the true index of the
789 target. 
790
791 We store in the name field of each syment the actual native index
792 applied so we can dig it out through a pointer.  */
793
794 static void 
795 DEFUN(coff_mangle_symbols,(bfd_ptr),
796       bfd *bfd_ptr)
797 {
798   unsigned int symbol_count = bfd_get_symcount(bfd_ptr);
799   asymbol **symbol_ptr_ptr = bfd_ptr->outsymbols;
800   struct internal_syment *last_tagndx = (struct internal_syment *)NULL;
801   struct internal_syment *last_file = (struct internal_syment *)NULL;
802   struct internal_syment *last_fcn = (struct internal_syment *)NULL;
803   struct internal_syment *block_stack[50];
804   struct internal_syment **last_block = &block_stack[0];
805   boolean first_time = true;  
806   unsigned int symbol_index;
807   unsigned int native_index = 0;
808
809   for (symbol_index = 0; symbol_index < symbol_count; symbol_index++) {
810     coff_symbol_type *coff_symbol_ptr =
811       coff_symbol_from(bfd_ptr, symbol_ptr_ptr[symbol_index]);
812     if (coff_symbol_ptr == (coff_symbol_type *)NULL) {
813       /* 
814         This symbol has no coff information in it, it will take up
815         only one slot in the output symbol table
816         */
817       native_index++;
818     }
819     else {
820       struct internal_syment *syment = coff_symbol_ptr->native;
821       if (syment == (struct internal_syment *)NULL) {
822         native_index++;
823       }
824       else {
825         /* Normalize the symbol flags */
826         if (coff_symbol_ptr->symbol.flags & BSF_FORT_COMM) {
827           /* a common symbol is undefined with a value */
828           syment->n_scnum = N_UNDEF;
829           syment->n_value = coff_symbol_ptr->symbol.value;
830         }
831         else if (coff_symbol_ptr->symbol.flags & BSF_DEBUGGING) {
832           syment->n_value = coff_symbol_ptr->symbol.value;
833         }
834         else if (coff_symbol_ptr->symbol.flags & BSF_UNDEFINED) {
835           syment->n_scnum = N_UNDEF;
836           syment->n_value = 0;
837         }         
838         else if (coff_symbol_ptr->symbol.flags & BSF_ABSOLUTE) {
839           syment->n_scnum = N_ABS;
840           syment->n_value = coff_symbol_ptr->symbol.value;
841         }         
842         else {
843           syment->n_scnum        = 
844             coff_symbol_ptr->symbol.section->output_section->index+1;
845           
846           syment->n_value = 
847             coff_symbol_ptr->symbol.value +
848               coff_symbol_ptr->symbol.section->output_offset +
849                 coff_symbol_ptr->symbol.section->output_section->vma;
850         }
851         
852         
853         /* If this symbol ties up something then do it */
854
855         if (syment->n_sclass == C_FILE && last_file != (struct internal_syment *)NULL)
856           {
857              last_file->n_value = native_index;
858           }
859         else if ((syment->n_sclass == C_EXT 
860                   || syment->n_sclass == C_STAT 
861 #ifdef C_LEAFEXT
862                   || syment->n_sclass == C_LEAFEXT 
863                   || syment->n_sclass == C_LEAFSTAT
864 #endif
865                   )
866                  && last_fcn != (struct internal_syment *)NULL) 
867             {
868               union internal_auxent *auxent = (union internal_auxent *)(last_fcn+1);
869               auxent->x_sym.x_fcnary.x_fcn.x_endndx = native_index;
870               last_fcn = (struct internal_syment *)NULL;
871               
872             }
873         else if (syment->n_sclass == C_EOS && last_tagndx != (struct internal_syment*)NULL)
874             {
875               union internal_auxent *auxent = (union internal_auxent *)(last_tagndx+1);
876               /* Remember that we keep the native index in the offset 
877                  so patch the beginning of the struct to point to this
878                  */
879               auxent->x_sym.x_tagndx =    last_tagndx->_n._n_n._n_offset;
880               auxent->x_sym.x_fcnary.x_fcn.x_endndx = syment->n_numaux + 1 + native_index;
881               /* Now point the eos to the structure */
882               auxent = (union internal_auxent *)(syment+1);
883               auxent->x_sym.x_tagndx =  last_tagndx->_n._n_n._n_offset;
884             }
885         else if (syment->n_sclass == C_BLOCK 
886                  && coff_symbol_ptr->symbol.name[1] == 'e') 
887             {
888               union internal_auxent *auxent = (union internal_auxent *)((*(--last_block))+1);
889               auxent->x_sym.x_fcnary.x_fcn.x_endndx = native_index + syment->n_numaux + 1;
890             }
891         if (syment->n_sclass == C_EXT 
892             && !ISFCN(syment->n_type) 
893             && first_time == true 
894             && last_file != (struct internal_syment *)NULL) {
895           /* This is the first external symbol seen which isn't a 
896              function place it in the last .file entry */
897           last_file->n_value = native_index;
898           first_time = false;
899         }
900 #ifdef C_LEAFPROC
901         if (syment->n_sclass == C_LEAFPROC &&
902             syment->n_numaux == 2) {
903           union internal_auxent *auxent = (union internal_auxent *)(syment+2);
904           /* This is the definition of a leaf proc, we'll relocate the 
905              address */
906           auxent->x_bal.x_balntry =       
907             coff_symbol_ptr->symbol.section->output_offset + 
908               coff_symbol_ptr->symbol.section->output_section->vma +
909                 auxent->x_bal.x_balntry   ;
910         }
911 #endif
912         /* If this symbol needs to be tied up then remember some facts */
913         if (syment->n_sclass == C_FILE) 
914             {
915               last_file = syment;
916             }
917         if (syment->n_numaux != 0) {
918           /*
919             If this symbol would like to point to something in the
920             future then remember where it is 
921             */
922           if (uses_x_sym_x_tagndx_p(bfd_ptr, syment)) {
923             /* 
924               If this is a ref to a structure then we'll tie it up 
925               now - there are never any forward refs for one 
926               */
927             if (syment->n_sclass == C_STRTAG ||
928                 syment->n_sclass == C_ENTAG ||
929                 syment->n_sclass == C_UNTAG) {
930               last_tagndx = syment;
931             }
932             else {
933               /*
934                 This is a ref to a structure - the structure must
935                 have been defined within the same file, and previous
936                 to this point, so we can deduce the new tagndx
937                 directly.
938                 */
939               union internal_auxent *auxent = (union internal_auxent *)(syment+1);
940               bfd *bfd_ptr = coff_symbol_ptr->symbol.the_bfd;
941               struct internal_syment *base = obj_raw_syments(bfd_ptr);        
942               auxent->x_sym.x_tagndx = base[auxent->x_sym.x_tagndx]._n._n_n._n_offset;
943               
944               
945             }
946           }
947           if (ISFCN(syment->n_type)) {
948             last_fcn = syment;
949           }
950           if (syment->n_sclass == C_BLOCK 
951               && coff_symbol_ptr->symbol.name[1] == 'b')
952               {
953                 *last_block++ = syment;
954               }
955         }
956         syment->_n._n_n._n_offset = native_index;
957         native_index = native_index + 1 + syment->n_numaux;
958       }
959     }
960   }
961 }
962
963
964 static void 
965 DEFUN(coff_write_symbols,(abfd),
966 bfd            *abfd)
967 {
968   unsigned int    i;
969   unsigned int    limit = bfd_get_symcount(abfd);
970   unsigned int    written = 0;
971   struct internal_syment          dummy;
972   asymbol       **p;
973   unsigned int    string_size = 0;
974     
975     
976   /* Seek to the right place */
977   bfd_seek(abfd, obj_sym_filepos(abfd), SEEK_SET);
978     
979   /* Output all the symbols we have */
980     
981   written = 0;
982   for (p = abfd->outsymbols, i = 0; i < limit; i++, p++) {
983     asymbol        *symbol = *p;
984     coff_symbol_type *c_symbol = coff_symbol_from(abfd, symbol);
985       
986     unsigned int    j;
987     struct internal_syment         *native;
988     if (c_symbol == (coff_symbol_type *) NULL ||
989         c_symbol->native == (struct internal_syment *) NULL) {
990       /*
991         This symbol has been created by the loader, or come from a non
992         coff format. It  has no native element to inherit, make our
993         own
994         */
995         
996       native = &dummy;
997       native->n_type =  T_NULL;
998 #ifdef I960
999       native->n_flags =  0;
1000 #endif
1001       if (symbol->flags & BSF_ABSOLUTE) {
1002         native->n_scnum  =  N_ABS;
1003         native->n_value =  symbol->value;
1004       }
1005       else if (symbol->flags & (BSF_UNDEFINED | BSF_FORT_COMM)) {
1006         native->n_scnum =  N_UNDEF;
1007         native->n_value =  symbol->value;
1008       }
1009       else if (symbol->flags & BSF_DEBUGGING) {
1010         /*
1011           remove name so it doesn't take up any space
1012           */
1013         symbol->name = "";
1014         continue;
1015       }
1016       else {
1017         native->n_scnum  =   symbol->section->output_section->index +
1018           1;
1019         native->n_value =   symbol->value +
1020           symbol->section->output_section->vma +
1021             symbol->section->output_offset;
1022 #ifdef I960
1023         /* Copy the any flags from the the file hdr into the symbol  */
1024           {
1025             coff_symbol_type *c = coff_symbol_from(abfd, symbol);
1026             if (c != (coff_symbol_type *)NULL) {
1027               native->n_flags =   c->symbol.the_bfd->flags;
1028             }
1029           }
1030 #endif
1031       }
1032         
1033 #ifdef HASPAD1
1034       native->pad1[0] = 0;
1035       native->pad1[0] = 0;
1036 #endif
1037         
1038       native->n_type =  0;
1039       if (symbol->flags & BSF_LOCAL)
1040         native->n_sclass =  C_STAT;
1041       else 
1042         native->n_sclass =  C_EXT;
1043       native->n_numaux =  0;
1044     }
1045     else
1046       /*
1047         Does this symbol have an ascociated line number - if so then
1048         make it remember this symbol index. Also tag the auxent of
1049         this symbol to point to the right place in the lineno table
1050         */
1051         {
1052           alent          *lineno = c_symbol->lineno;
1053           native = c_symbol->native;
1054           if (lineno) {
1055             unsigned int    count = 0;
1056             lineno[count].u.offset = written;
1057             if (native->n_numaux) {
1058               union internal_auxent  *a = (union internal_auxent *) (native + 1);
1059                 
1060               a->x_sym.x_fcnary.x_fcn.x_lnnoptr =  
1061                 c_symbol->symbol.section->output_section->moving_line_filepos;
1062             }
1063             /*
1064               And count and relocate all other linenumbers
1065               */
1066             count++;
1067             while (lineno[count].line_number) {
1068               lineno[count].u.offset +=
1069                 c_symbol->symbol.section->output_section->vma +
1070                   c_symbol->symbol.section->output_offset;
1071               count++;
1072             }
1073             c_symbol->symbol.section->output_section->moving_line_filepos +=
1074               count * LINESZ;
1075               
1076           }
1077         }                       /* if symbol new to coff */
1078       
1079     /* Fix the symbol names */
1080       {
1081         unsigned int    name_length;
1082         if (symbol->name == (char *) NULL) {
1083           /*
1084             coff symbols always have names, so we'll make one up
1085             */
1086           symbol->name = "strange";
1087         }
1088         name_length = strlen(symbol->name);
1089         if (name_length <= SYMNMLEN) {
1090           /* This name will fit into the symbol neatly */
1091           strncpy(native->_n._n_name, symbol->name, SYMNMLEN);
1092         }
1093         else {
1094           native->_n._n_n._n_offset =  string_size + 4;
1095           native->_n._n_n._n_zeroes = 0;
1096           string_size += name_length + 1;
1097         }
1098           {
1099             unsigned int    numaux = native->n_numaux;
1100             int             type = native->n_type;
1101             int             class =  native->n_sclass;
1102             SYMENT buf;
1103             bfd_coff_swap_sym_out(abfd, native, &buf);
1104             bfd_write((PTR)& buf, 1, SYMESZ, abfd);
1105             for (j = 0; j != native->n_numaux;
1106                  j++) {
1107               AUXENT buf1;
1108               bfd_coff_swap_aux_out(abfd,
1109                                     (union internal_auxent *)(native + j + 1), type, class, &buf1);
1110               bfd_write((PTR) (native + j + 1), 1, AUXESZ, abfd);
1111             }
1112             /*
1113               Reuse somewhere in the symbol to keep the index
1114               */
1115             set_index(symbol, written);
1116             written += 1 + numaux;
1117           }
1118       }
1119   }                             /* for each out symbol */
1120     
1121   bfd_get_symcount(abfd) = written;
1122   /* Now write out strings */
1123     
1124   if (string_size) {
1125     unsigned int    size = string_size + 4;
1126     size =  size;
1127     bfd_write((PTR) &size, 1, sizeof(size), abfd);
1128     for (p = abfd->outsymbols, i = 0; i < limit; i++, p++) {
1129       asymbol        *q = *p;
1130       size_t          name_length = strlen(q->name);
1131       if (name_length > SYMNMLEN) {
1132         bfd_write((PTR) (q->name), 1, name_length + 1, abfd);
1133       }
1134     }
1135   }
1136   else {
1137     /* We would normally not write anything here, but we'll write
1138        out 4 so that any stupid coff reader which tries to read
1139        the string table even when there isn't one won't croak.
1140        */
1141       
1142     uint32e_type size = 4;
1143     size =  size;
1144     bfd_write((PTR)&size, 1, sizeof(size), abfd);
1145       
1146   }
1147     
1148 }
1149
1150 static void 
1151 coff_write_relocs(abfd)
1152 bfd            *abfd;
1153   {
1154     asection       *s;
1155     for (s = abfd->sections; s != (asection *) NULL; s = s->next) {
1156       unsigned int    i;
1157       struct external_reloc dst;
1158       
1159       arelent       **p = s->orelocation;
1160       bfd_seek(abfd, s->rel_filepos, SEEK_SET);
1161       for (i = 0; i < s->reloc_count; i++) {
1162         struct internal_reloc    n;
1163         arelent        *q = p[i];
1164         memset((PTR)&n, 0, sizeof(n));
1165         n.r_vaddr = q->address + s->vma;
1166         if (q->sym_ptr_ptr) {
1167           n.r_symndx = get_index((*(q->sym_ptr_ptr)));
1168         }
1169 #ifdef SELECT_RELOC
1170         /* Work out reloc type from what is required */
1171         SELECT_RELOC(n.r_type, q->howto);
1172 #else
1173         n.r_type = q->howto->type;
1174 #endif
1175         bfd_swap_reloc_out(abfd, &n, &dst);
1176         bfd_write((PTR) &n, 1, RELSZ, abfd);
1177       }
1178     }
1179   }
1180
1181 static void 
1182 DEFUN(coff_write_linenumbers,(abfd),
1183       bfd            *abfd)
1184   {
1185     asection       *s;
1186     for (s = abfd->sections; s != (asection *) NULL; s = s->next) {
1187       if (s->lineno_count) {
1188         asymbol       **q = abfd->outsymbols;
1189         bfd_seek(abfd, s->line_filepos, SEEK_SET);
1190         /* Find all the linenumbers in this section */
1191         while (*q) {
1192           asymbol        *p = *q;
1193           alent          *l = BFD_SEND(p->the_bfd, _get_lineno, (p->the_bfd, p));
1194           if (l) {
1195             /* Found a linenumber entry, output */
1196             struct internal_lineno  out;
1197             LINENO buff;
1198             bzero( (PTR)&out, sizeof(out));
1199             out.l_lnno = 0;
1200             out.l_addr.l_symndx = l->u.offset;
1201             bfd_coff_swap_lineno_out(abfd, &out, &buff);
1202             bfd_write((PTR) &buff, 1, LINESZ, abfd);
1203             l++;
1204             while (l->line_number) {
1205               out.l_lnno = l->line_number;
1206               out.l_addr.l_symndx = l->u.offset;
1207               bfd_coff_swap_lineno_out(abfd, &out, &buff);
1208               bfd_write((PTR) &buff, 1, LINESZ, abfd);
1209               l++;
1210             }
1211           }
1212           q++;
1213         }
1214       }
1215     }
1216   }
1217
1218
1219 static asymbol *
1220 coff_make_empty_symbol(abfd)
1221 bfd            *abfd;
1222   {
1223     coff_symbol_type *new = (coff_symbol_type *) bfd_alloc(abfd, sizeof(coff_symbol_type));
1224     if (new == NULL) {
1225       bfd_error = no_memory;
1226       return (NULL);
1227     }                   /* on error */
1228     new->native = 0;
1229     new->lineno = (alent *) NULL;
1230     new->symbol.the_bfd = abfd;
1231     return &new->symbol;
1232   }
1233
1234 static void 
1235 coff_print_symbol(ignore_abfd, file, symbol, how)
1236 bfd            *ignore_abfd;
1237 FILE           *file;
1238 asymbol        *symbol;
1239 bfd_print_symbol_enum_type how;
1240   {
1241     switch (how) {
1242     case bfd_print_symbol_name_enum:
1243       fprintf(file, "%s", symbol->name);
1244       break;
1245     case bfd_print_symbol_type_enum:
1246       fprintf(file, "coff %lx %lx", (unsigned long) coffsymbol(symbol)->native,
1247               (unsigned long) coffsymbol(symbol)->lineno);
1248       break;
1249     case bfd_print_symbol_all_enum:
1250         {
1251           CONST char           *section_name = symbol->section == (asection *) NULL ?
1252             "*abs" : symbol->section->name;
1253           bfd_print_symbol_vandf((PTR) file, symbol);
1254           
1255           fprintf(file, " %-5s %s %s %s",
1256                   section_name,
1257                   coffsymbol(symbol)->native ? "n" : "g",
1258                   coffsymbol(symbol)->lineno ? "l" : " ",
1259                   symbol->name);
1260         }
1261       
1262       
1263       break;
1264     }
1265   }
1266
1267 static alent   *
1268 coff_get_lineno(ignore_abfd, symbol)
1269 bfd            *ignore_abfd;
1270 asymbol        *symbol;
1271   {
1272     return coffsymbol(symbol)->lineno;
1273   }
1274
1275 /*
1276 Set flags and magic number of a coff file from architecture and machine
1277 type.  Result is true if we can represent the arch&type, false if not.
1278 */
1279 static          boolean
1280 coff_set_flags(abfd, magicp, flagsp)
1281 bfd            *abfd;
1282 unsigned       *magicp,
1283 *flagsp;
1284   {
1285     
1286     switch (abfd->obj_arch) {
1287       
1288 #ifdef I960ROMAGIC
1289       
1290     case bfd_arch_i960:
1291       
1292         {
1293           unsigned        flags;
1294           *magicp = I960ROMAGIC;
1295           /*
1296             ((bfd_get_file_flags(abfd) & WP_TEXT) ? I960ROMAGIC :
1297              I960RWMAGIC);   FIXME???
1298                */
1299           switch (abfd->obj_machine) {
1300           case bfd_mach_i960_core:
1301             flags = F_I960CORE;
1302             break;
1303           case bfd_mach_i960_kb_sb:
1304             flags = F_I960KB;
1305             break;
1306           case bfd_mach_i960_mc:
1307             flags = F_I960MC;
1308             break;
1309           case bfd_mach_i960_xa:
1310             flags = F_I960XA;
1311             break;
1312           case bfd_mach_i960_ca:
1313             flags = F_I960CA;
1314             break;
1315           case bfd_mach_i960_ka_sa:
1316             flags = F_I960KA;
1317             break;
1318           default:
1319             return false;
1320           }
1321           *flagsp = flags;
1322           return true;
1323         }
1324         break;
1325 #endif
1326 #ifdef MIPS
1327       case bfd_arch_mips:
1328           *magicp = MIPS_MAGIC_2;
1329         return true;
1330         break;
1331 #endif
1332 #ifdef MC68MAGIC
1333       case bfd_arch_m68k:
1334         *magicp = MC68MAGIC;
1335         return true;
1336 #endif
1337         
1338 #ifdef MC88MAGIC
1339       case bfd_arch_m88k:
1340         *magicp = MC88OMAGIC;
1341         return true;
1342         break;
1343 #endif
1344         
1345       default:          /* Unknown architecture */
1346         return false;
1347       }
1348     
1349     return false;
1350   }
1351
1352
1353 static          boolean
1354 coff_set_arch_mach(abfd, arch, machine)
1355 bfd            *abfd;
1356 enum bfd_architecture arch;
1357 unsigned long   machine;
1358   {
1359     unsigned        dummy1,
1360     dummy2;
1361     abfd->obj_arch = arch;
1362     abfd->obj_machine = machine;
1363     if (arch != bfd_arch_unknown &&
1364         coff_set_flags(abfd, &dummy1, &dummy2) != true)
1365       return false;             /* We can't represent this type */
1366     return true;        /* We're easy ... */
1367   }
1368
1369
1370 /* Calculate the file position for each section. */
1371
1372 static void 
1373 coff_compute_section_file_positions(abfd)
1374 bfd            *abfd;
1375   {
1376     asection       *current;
1377     file_ptr        sofar = FILHSZ;
1378     if (bfd_get_start_address(abfd)) {
1379       /*
1380         A start address may have been added to the original file. In this
1381         case it will need an optional header to record it.
1382           */
1383       abfd->flags |= EXEC_P;
1384     }
1385     if (abfd->flags & EXEC_P)
1386       sofar += AOUTSZ;
1387     
1388     
1389     sofar += abfd->section_count * SCNHSZ;
1390     
1391     for (current = abfd->sections; current != NULL; current =
1392          current->next) {
1393       /* Only deal with sections which have contents */
1394       if (!(current->flags & SEC_HAS_CONTENTS))
1395         continue;
1396       
1397       /* Align the sections in the file to the same boundary on 
1398         which they are aligned in virtual memory.  I960 doesn't
1399           do this (FIXME) so we can stay in sync with Intel.  960
1400             doesn't yet page from files... */
1401 #ifndef I960
1402       sofar = ALIGN(sofar, 1 << current->alignment_power);
1403 #endif
1404       /* FIXME, in demand paged files, the low order bits of the file
1405         offset must match the low order bits of the virtual address.
1406           "Low order" is apparently implementation defined.  Add code
1407             here to round sofar up to match the virtual address.  */
1408       
1409       current->filepos = sofar;
1410       sofar += current->size;
1411     }
1412     obj_relocbase(abfd) = sofar;
1413   }
1414
1415
1416
1417
1418 /* SUPPRESS 558 */
1419 /* SUPPRESS 529 */
1420 static          boolean
1421 DEFUN(coff_write_object_contents,(abfd),
1422 bfd            *abfd)
1423 {
1424   asection       *current;
1425   boolean         hasrelocs = false;
1426   boolean         haslinno = false;
1427   file_ptr        reloc_base;
1428   file_ptr        lineno_base;
1429   file_ptr        sym_base;
1430   file_ptr        scn_base;
1431   file_ptr        data_base;
1432   unsigned long   reloc_size = 0;
1433   unsigned long   lnno_size = 0;
1434   asection       *text_sec = NULL;
1435   asection       *data_sec = NULL;
1436   asection       *bss_sec = NULL;
1437
1438   struct internal_filehdr internal_f;
1439   struct internal_aouthdr internal_a;
1440     
1441   struct icofdata *coff = obj_icof(abfd);
1442     
1443     
1444   bfd_error = system_call_error;
1445     
1446     
1447   if(abfd->output_has_begun == false) {
1448     coff_compute_section_file_positions(abfd);
1449   }
1450     
1451   if (abfd->sections != (asection *)NULL) {
1452     scn_base = abfd->sections->filepos;
1453   }
1454   else {
1455     scn_base = 0;
1456   }
1457   if (bfd_seek(abfd, scn_base, SEEK_SET) != 0)
1458     return false;
1459   reloc_base = obj_relocbase(abfd);
1460     
1461   /* Make a pass through the symbol table to count line number entries and
1462      put them into the correct asections */
1463     
1464   coff_count_linenumbers(abfd);
1465   data_base = scn_base;
1466     
1467   /* Work out the size of the reloc and linno areas */
1468     
1469   for (current = abfd->sections; current != NULL; current = current->next) {
1470     reloc_size += current->reloc_count * RELSZ;
1471     lnno_size += current->lineno_count * LINESZ;
1472     data_base += SCNHSZ;
1473   }
1474     
1475   lineno_base = reloc_base + reloc_size;
1476   sym_base = lineno_base + lnno_size;
1477     
1478   /* Indicate in each section->line_filepos its actual file address */
1479   for (current = abfd->sections; current != NULL; current = current->next) {
1480     if (current->lineno_count) {
1481       current->line_filepos = lineno_base;
1482       current->moving_line_filepos = lineno_base;
1483       lineno_base += current->lineno_count * LINESZ;
1484     }
1485     else {
1486       current->line_filepos = 0;
1487     }
1488     if (current->reloc_count) {
1489       current->rel_filepos = reloc_base;
1490       reloc_base += current->reloc_count * sizeof(struct internal_reloc);
1491     }
1492     else {
1493       current->rel_filepos = 0;
1494     }
1495   }
1496     
1497   /* Write section headers to the file.  */
1498     
1499   bfd_seek(abfd,
1500            (file_ptr) ((abfd->flags & EXEC_P) ?
1501                        (FILHSZ + AOUTSZ) : FILHSZ),
1502            SEEK_SET);
1503     
1504     {
1505 #if 0
1506       unsigned int    pad = abfd->flags & D_PAGED ? data_base : 0;
1507 #endif
1508       unsigned int    pad = 0;
1509         
1510       for (current = abfd->sections; current != NULL; current = current->next) {
1511         struct internal_scnhdr section;
1512         strncpy(&(section.s_name[0]), current->name, 8);
1513         section.s_vaddr = current->vma + pad;
1514         section.s_paddr = current->vma + pad;
1515         section.s_size = current->size - pad;
1516         /*
1517           If this section has no size or is unloadable then the scnptr
1518           will be 0 too
1519           */
1520         if (current->size - pad == 0 ||
1521             (current->flags & SEC_LOAD) == 0) {
1522           section.s_scnptr = 0;
1523             
1524         }
1525         else {
1526           section.s_scnptr = current->filepos;
1527         }
1528         section.s_relptr = current->rel_filepos;
1529         section.s_lnnoptr = current->line_filepos;
1530         section.s_nreloc = current->reloc_count;
1531         section.s_nlnno = current->lineno_count;
1532         if (current->reloc_count != 0)
1533           hasrelocs = true;
1534         if (current->lineno_count != 0)
1535           haslinno = true;
1536           
1537         if (!strcmp(current->name, _TEXT)) {
1538           text_sec = current;
1539           section.s_flags = STYP_TEXT; /* kinda stupid */
1540         }
1541         else if (!strcmp(current->name, _DATA)) {
1542           data_sec = current;
1543           section.s_flags = STYP_DATA; /* kinda stupid */
1544         }
1545         else if (!strcmp(current->name, _BSS)) {
1546           bss_sec = current;
1547           section.s_flags = STYP_BSS; /* kinda stupid */
1548         }
1549           
1550           
1551 #ifdef I960
1552         section.s_align = (current->alignment_power
1553                            ? 1 << current->alignment_power
1554                            : 0);
1555
1556 #endif
1557           {
1558             SCNHDR          buff;
1559
1560             swap_scnhdr_out(abfd, &section, &buff);
1561             bfd_write((PTR) (&buff), 1, SCNHSZ, abfd);
1562
1563           }
1564         pad = 0;
1565       }
1566     }
1567
1568   /* OK, now set up the filehdr... */
1569   internal_f.f_nscns = abfd->section_count;
1570   /*
1571     We will NOT put a fucking timestamp in the header here. Every time you
1572     put it back, I will come in and take it out again. I'm sorry. This
1573     field does not belong here.  We fill it with a 0 so it compares the
1574     same but is not a reasonable time. -- gnu@cygnus.com
1575     */
1576   /*
1577     Well, I like it, so I'm conditionally compiling it in.
1578     steve@cygnus.com
1579     */
1580 #ifdef COFF_TIMESTAMP
1581   internal_f.f_timdat = time(0);
1582 #else
1583   internal_f.f_timdat = 0;
1584 #endif
1585
1586   if (bfd_get_symcount(abfd) != 0)
1587     internal_f.f_symptr = sym_base;
1588   else
1589     internal_f.f_symptr = 0;
1590
1591   internal_f.f_flags = 0;
1592
1593   if (abfd->flags & EXEC_P)
1594     internal_f.f_opthdr = AOUTSZ;
1595   else
1596     internal_f.f_opthdr = 0;
1597
1598   if (!hasrelocs)
1599     internal_f.f_flags |= F_RELFLG;
1600   if (!haslinno)
1601     internal_f.f_flags |= F_LNNO;
1602   if (0 == bfd_get_symcount(abfd))
1603     internal_f.f_flags |= F_LSYMS;
1604   if (abfd->flags & EXEC_P)
1605     internal_f.f_flags |= F_EXEC;
1606 #if M88
1607   internal_f.f_flags |= F_AR32W;
1608 #else
1609   if (!abfd->xvec->byteorder_big_p)
1610     internal_f.f_flags |= F_AR32WR;
1611 #endif
1612   /*
1613     FIXME, should do something about the other byte orders and
1614     architectures.
1615     */
1616
1617   /* Set up architecture-dependent stuff */
1618
1619     { int   magic = 0;
1620       int   flags = 0;
1621       coff_set_flags(abfd, &magic, &flags);
1622       internal_f.f_magic = magic;
1623       internal_f.f_flags = flags;
1624
1625       /* ...and the "opt"hdr... */
1626
1627 #ifdef I960
1628       internal_a.magic = (magic == I960ROMAGIC ? NMAGIC : OMAGIC); 
1629 #endif
1630 #if M88
1631       internal_a.magic = PAGEMAGICBCS;
1632 #endif
1633     }
1634   /* Now should write relocs, strings, syms */
1635   obj_sym_filepos(abfd) = sym_base;
1636
1637   if (bfd_get_symcount(abfd) != 0) {
1638     coff_mangle_symbols(abfd);
1639     coff_write_symbols(abfd);
1640     coff_write_linenumbers(abfd);
1641     coff_write_relocs(abfd);
1642   }
1643   if (text_sec) {
1644     internal_a.tsize = text_sec->size;
1645     internal_a.text_start =text_sec->size ? text_sec->vma : 0;
1646   }
1647   if (data_sec) {
1648     internal_a.dsize = data_sec->size;
1649     internal_a.data_start = data_sec->size ? data_sec->vma      : 0;
1650   }
1651   if (bss_sec) {
1652     internal_a.bsize =  bss_sec->size;
1653   }
1654
1655   internal_a.entry = bfd_get_start_address(abfd);
1656   internal_f.f_nsyms =  bfd_get_symcount(abfd);
1657
1658   /* now write them */
1659   if (bfd_seek(abfd, 0L, SEEK_SET) != 0)
1660     return false;
1661     {
1662       FILHDR buff;
1663       bfd_swap_filehdr_out(abfd, &internal_f, &buff);
1664       bfd_write((PTR) &buff, 1, FILHSZ, abfd);
1665     }
1666   if (abfd->flags & EXEC_P) {
1667     AOUTHDR buff;
1668     bfd_swap_aouthdr_out(abfd, &internal_a, &buff);
1669     bfd_write((PTR) &buff, 1, AOUTSZ, abfd);
1670   }
1671   return true;
1672 }
1673
1674 static          boolean
1675 coff_set_section_contents(abfd, section, location, offset, count)
1676     bfd            *abfd;
1677     sec_ptr         section;
1678     PTR             location;
1679     file_ptr        offset;
1680     size_t          count;
1681 {
1682     if (abfd->output_has_begun == false)        /* set by bfd.c handler */
1683         coff_compute_section_file_positions(abfd);
1684
1685     bfd_seek(abfd, (file_ptr) (section->filepos + offset), SEEK_SET);
1686
1687     if (count != 0) {
1688         return (bfd_write(location, 1, count, abfd) == count) ? true : false;
1689     }
1690     return true;
1691 }
1692
1693 static          boolean
1694 coff_close_and_cleanup(abfd)
1695     bfd            *abfd;
1696 {
1697   if (!bfd_read_p(abfd))
1698     switch (abfd->format) {
1699     case bfd_archive:
1700       if (!_bfd_write_archive_contents(abfd))
1701         return false;
1702       break;
1703     case bfd_object:
1704       if (!coff_write_object_contents(abfd))
1705         return false;
1706       break;
1707     default:
1708       bfd_error = invalid_operation;
1709       return false;
1710     }
1711
1712   /* We depend on bfd_close to free all the memory on the obstack.  */
1713   /* FIXME if bfd_release is not using obstacks! */
1714   return true;
1715 }
1716
1717
1718 static PTR 
1719 buy_and_read(abfd, where, seek_direction, size)
1720     bfd            *abfd;
1721     file_ptr        where;
1722     int             seek_direction;
1723     size_t          size;
1724 {
1725     PTR             area = (PTR) bfd_alloc(abfd, size);
1726     if (!area) {
1727         bfd_error = no_memory;
1728         return (NULL);
1729     }
1730     bfd_seek(abfd, where, seek_direction);
1731     if (bfd_read(area, 1, size, abfd) != size) {
1732         bfd_error = system_call_error;
1733         return (NULL);
1734     }                           /* on error */
1735     return (area);
1736 }                               /* buy_and_read() */
1737
1738 static void 
1739 DEFUN(offset_symbol_indices,(abfd, symtab, count, offset),
1740       bfd *abfd AND
1741       struct internal_syment         *symtab AND
1742       unsigned long   count AND
1743       long            offset)
1744 {
1745   struct internal_syment         *end = symtab + count;
1746   for (; symtab < end; ++symtab) {
1747     if (symtab->n_sclass == C_FILE) {
1748       symtab->n_value = 0;
1749     }
1750     else if (symtab->n_sclass == C_ALIAS) {
1751       /*
1752         These guys have indices in their values.
1753         */
1754       symtab->n_value = symtab->n_value + offset;
1755     }
1756     else if (symtab->n_numaux) {
1757       /*
1758         anybody else without an aux, has no indices.
1759         */
1760       
1761       if (symtab->n_sclass == C_EOS
1762           || (BTYPE(symtab->n_type) == T_STRUCT
1763               && symtab->n_sclass != C_STRTAG)
1764           || BTYPE(symtab->n_type) == T_UNION
1765           || BTYPE(symtab->n_type) == T_ENUM) {
1766         /* If the tagndx is 0 then the struct hasn't really been
1767            defined, so leave it alone */
1768         
1769         if(((union internal_auxent *) (symtab + 1))->x_sym.x_tagndx != 0) {
1770           ((union internal_auxent *) (symtab + 1))->x_sym.x_tagndx += offset;
1771         }
1772         
1773       }                         /* These guys have a tagndx */
1774       if (symtab->n_sclass == C_STRTAG
1775           || symtab->n_sclass == C_UNTAG
1776           || symtab->n_sclass == C_ENTAG
1777           || symtab->n_sclass == C_BLOCK
1778           || symtab->n_sclass == C_FCN
1779           || ISFCN(symtab->n_type)) {
1780         
1781         ((union internal_auxent *) (symtab +
1782                                     1))->x_sym.x_fcnary.x_fcn.x_endndx
1783                                       += offset;
1784         
1785       }                         /* These guys have an endndx */
1786 #ifndef I960
1787       if (ISFCN(symtab->n_type)) {
1788         ((union internal_auxent *) (symtab + 1))->x_sym.x_tvndx += offset;
1789       }                         /* These guys have a tvndx.  I think...
1790                                    (FIXME) */
1791 #endif                          /* Not I960 */
1792       
1793     }                           /* if value, else if aux */
1794     symtab += symtab->n_numaux;
1795   }                             /* walk the symtab */
1796   
1797   return;
1798 }                               /* offset_symbol_indices() */
1799
1800 #if 0
1801 /* swap the entire symbol table - we c*/
1802 static void 
1803 swap_raw_symtab(abfd, raw_symtab)
1804 bfd            *abfd;
1805 SYMENT         *raw_symtab;
1806   {
1807     long            i;
1808     SYMENT         *end = raw_symtab + bfd_get_symcount(abfd);
1809     for (; raw_symtab < end; ++raw_symtab) {
1810       bfd_coff_swap_sym(abfd, raw_symtab);
1811       
1812       for (i = raw_symtab->n_numaux; i; --i, ++raw_symtab) {
1813         bfd_coff_swap_aux(abfd,
1814                           (AUXENT *)(raw_symtab + 1),
1815                           raw_symtab->n_type,
1816                           raw_symtab->n_sclass);
1817       }                         /* swap all the aux entries */
1818     }                           /* walk the symbol table */
1819     
1820     return;
1821   }                             /* swap_raw_symtab() */
1822 #endif
1823 /*
1824 read a symbol table into freshly mallocated memory, swap it, and knit the
1825 symbol names into a normalized form. By normalized here I mean that all
1826 symbols have an n_offset pointer that points to a NULL terminated string.
1827 Oh, and the first symbol MUST be a C_FILE.  If there wasn't one there
1828 before, put one there.
1829 */
1830
1831 static struct internal_syment  *
1832 DEFUN(get_normalized_symtab,(abfd),
1833 bfd            *abfd)
1834 {
1835
1836   struct internal_syment         *internal;
1837   struct internal_syment         *internal_ptr;
1838   struct internal_syment         *internal_end;
1839   SYMENT *raw;
1840   SYMENT *raw_src;
1841   SYMENT *raw_end;
1842   char           *string_table = NULL;
1843   unsigned long   size;
1844   char string_table_size_buffer[4];
1845   unsigned long   string_table_size = 0;
1846   unsigned int raw_size;
1847   if (obj_raw_syments(abfd) != (struct internal_syment *)NULL) {
1848     return obj_raw_syments(abfd);
1849   }
1850   if ((size = bfd_get_symcount(abfd) * sizeof(struct internal_syment)) == 0) {
1851     bfd_error = no_symbols;
1852     return (NULL);
1853   }
1854
1855   internal = (struct internal_syment *)bfd_alloc(abfd, size);
1856   internal_end = internal + bfd_get_symcount(abfd);
1857
1858   raw_size =      bfd_get_symcount(abfd) * SYMESZ;
1859   raw = (SYMENT *)bfd_alloc(abfd,raw_size);
1860
1861   if (bfd_seek(abfd, obj_sym_filepos(abfd), SEEK_SET) == -1
1862       || bfd_read((PTR)raw, raw_size, 1, abfd) != raw_size) {
1863     bfd_error = system_call_error;
1864     return (NULL);
1865   }
1866   /* mark the end of the symbols */
1867   raw_end = raw + bfd_get_symcount(abfd);
1868   /*
1869     FIXME SOMEDAY.  A string table size of zero is very weird, but
1870     probably possible.  If one shows up, it will probably kill us.
1871     */
1872
1873   /* Swap all the raw entries */
1874   for (raw_src = raw, internal_ptr = internal; raw_src < raw_end; raw_src++, internal_ptr++) {
1875     unsigned int i;
1876     bfd_coff_swap_sym_in(abfd, raw_src,internal_ptr);    
1877     for (i = internal_ptr->n_numaux; i; --i, raw_src++, internal_ptr++) {
1878       bfd_coff_swap_aux_in(abfd, (AUXENT *)(raw_src +1), internal_ptr->n_type,
1879                            internal_ptr->n_sclass, (union
1880                                                     internal_auxent *)(internal_ptr +1));
1881     }
1882   }
1883       
1884   /* Free all the raw stuff */
1885   bfd_release(abfd, raw_src);
1886
1887   for (internal_ptr = internal; internal_ptr < internal_end; internal_ptr ++) {
1888
1889     if (internal_ptr->_n._n_n._n_zeroes != 0) {
1890       /*
1891         This is a "short" name.  Make it long.
1892         */
1893       unsigned long   i = 0;
1894       char           *newstring = NULL;
1895       /*
1896         find the length of this string without walking into memory
1897         that isn't ours.
1898         */
1899         
1900       for (i = 0; i < 8; ++i) {
1901         if (internal_ptr->_n._n_name[i] == '\0') {
1902           break;
1903         }                       /* if end of string */
1904       }                         /* possible lengths of this string. */
1905         
1906       if ((newstring = (PTR) bfd_alloc(abfd, ++i)) == NULL) {
1907         bfd_error = no_memory;
1908         return (NULL);
1909       }                         /* on error */
1910       bzero(newstring, i);
1911       strncpy(newstring, internal_ptr->_n._n_name, i-1);
1912       internal_ptr->_n._n_n._n_offset =  (int) newstring;
1913       internal_ptr->_n._n_n._n_zeroes = 0;
1914         
1915     }
1916     else {
1917       if (string_table == NULL) {
1918         /*
1919           NOTE: we don't read the string table until now because we
1920           don't necessarily know that we have one until now.
1921           */
1922         /*
1923           At this point we should be "seek"'d to the end of the
1924           symbols === the symbol table size.
1925           */
1926           
1927         if (bfd_read((char *) string_table_size_buffer,
1928                      sizeof(string_table_size_buffer),
1929                      1, abfd) != sizeof(string_table_size)) {
1930           bfd_error = system_call_error;
1931           return (NULL);
1932         }                       /* on error */
1933           
1934         string_table_size = bfd_h_getlong(abfd, string_table_size_buffer);
1935           
1936         if ((string_table = (PTR) bfd_alloc(abfd, string_table_size -= 4)) == NULL) {
1937           bfd_error = no_memory;
1938           return (NULL);
1939         }                       /* on mallocation error */
1940         if (bfd_read(string_table, string_table_size, 1, abfd) != string_table_size) {
1941           bfd_error = system_call_error;
1942           return (NULL);
1943         }                       /* on error */
1944       }                         /* have not yet read the string table. */
1945       /*
1946         This is a long name already. Just point it at the string in
1947         memory.
1948         */
1949       internal_ptr->_n._n_n._n_offset = (int) (string_table - 4 +  internal_ptr->_n._n_n._n_offset);
1950
1951     }                           /* switch on type of symbol name */
1952       
1953     internal_ptr += internal_ptr->n_numaux;
1954   }                             /* for each symbol */
1955 #if 0
1956 #ifndef GNU960
1957   /* I'm not sure of the repercussions of this, so the Intel
1958      folks will always do the force
1959      */
1960   if (obj_symbol_slew(abfd) > 0) 
1961     force_indices_file_symbol_relative(abfd, internal);
1962 #else
1963   force_indices_file_symbol_relative(abfd, internal);
1964 #endif
1965 #endif
1966   obj_raw_syments(abfd) = internal;
1967   obj_string_table(abfd) = string_table;
1968     
1969   return (internal);
1970 }                               /* get_normalized_symtab() */
1971
1972 static
1973 struct sec *
1974 DEFUN(section_from_bfd_index,(abfd, index),
1975       bfd            *abfd AND
1976       int             index)
1977 {
1978   if (index > 0) {
1979     struct sec *answer = abfd->sections;
1980     while (--index) {
1981       answer = answer->next;
1982     }
1983     return answer;
1984   }
1985   return 0;
1986 }
1987
1988
1989
1990
1991 static boolean
1992 coff_slurp_line_table(abfd, asect)
1993 bfd            *abfd;
1994 asection       *asect;
1995   {
1996     LINENO  *native_lineno;
1997     alent          *lineno_cache;
1998     
1999     BFD_ASSERT(asect->lineno == (alent *) NULL);
2000     
2001     native_lineno = (LINENO *) buy_and_read(abfd,
2002                                             asect->line_filepos,
2003                                             SEEK_SET,
2004                                             (size_t) (LINESZ *
2005                                                       asect->lineno_count));
2006     lineno_cache =
2007       (alent *) bfd_alloc(abfd, (size_t) ((asect->lineno_count + 1) * sizeof(alent)));
2008     if (lineno_cache == NULL) {
2009       bfd_error = no_memory;
2010       return false;
2011     } else {    
2012       unsigned int    counter = 0;
2013       alent          *cache_ptr = lineno_cache;
2014       LINENO  *src = native_lineno;
2015       
2016       while (counter < asect->lineno_count) {
2017         struct internal_lineno dst;
2018         bfd_coff_swap_lineno_in(abfd, src, &dst);
2019         cache_ptr->line_number = dst.l_lnno;
2020         
2021         if (cache_ptr->line_number == 0) {
2022           coff_symbol_type *sym =
2023             (coff_symbol_type *) (dst.l_addr.l_symndx
2024                                   + obj_symbol_slew(abfd)
2025                                   + obj_raw_syments(abfd))->_n._n_n._n_zeroes;
2026           cache_ptr->u.sym = (asymbol *) sym;
2027           sym->lineno = cache_ptr;
2028         }
2029         else {
2030           cache_ptr->u.offset = dst.l_addr.l_paddr
2031             - bfd_section_vma(abfd, asect);
2032         }                               /* If no linenumber expect a symbol index */
2033         
2034         cache_ptr++;
2035         src++;
2036         counter++;
2037       }
2038       cache_ptr->line_number = 0;
2039       
2040     }
2041     asect->lineno = lineno_cache;
2042     /* FIXME, free native_lineno here, or use alloca or something. */
2043     return true;
2044   }                             /* coff_slurp_line_table() */
2045
2046 static struct internal_syment  *
2047 DEFUN(find_next_file_symbol,(abfd, current, end),
2048       bfd *abfd AND
2049       struct internal_syment *current AND
2050       struct internal_syment *end)
2051 {
2052   current += current->n_numaux + 1;
2053     
2054   while (current < end) {
2055     if (current->n_sclass== C_FILE) {
2056       return (current);
2057     }   
2058     current += current->n_numaux + 1;
2059   }
2060   return end;
2061 }
2062
2063
2064 /*
2065 Note that C_FILE symbols can, and some do, have more than 1 aux entry.
2066 */
2067
2068 static void
2069 DEFUN(force_indices_file_symbol_relative,(abfd, symtab),
2070       bfd            *abfd AND
2071      struct internal_syment         *symtab)
2072 {
2073   struct internal_syment         *end = symtab + bfd_get_symcount(abfd);
2074   struct internal_syment         *current;
2075   struct internal_syment         *next;
2076   /* the first symbol had damn well better be a C_FILE. */
2077   BFD_ASSERT(symtab->n_sclass == C_FILE);
2078     
2079   for (current = find_next_file_symbol(abfd, symtab, end);
2080        current < end;
2081        current = next) {
2082     offset_symbol_indices(abfd, current,
2083                           ((next =
2084                             find_next_file_symbol(abfd, current,
2085                                                   end)) - current),
2086                           symtab - current);
2087   }
2088   return;
2089 }       
2090
2091 static          boolean
2092 DEFUN(coff_slurp_symbol_table,(abfd),
2093       bfd            *abfd)
2094   {
2095     struct internal_syment         *native_symbols;
2096     coff_symbol_type *cached_area;
2097     unsigned int   *table_ptr;
2098     
2099     unsigned int    number_of_symbols = 0;
2100     if (obj_symbols(abfd))
2101       return true;
2102     bfd_seek(abfd, obj_sym_filepos(abfd), SEEK_SET);
2103     
2104     /* Read in the symbol table */
2105     if ((native_symbols = get_normalized_symtab(abfd)) == NULL) {
2106       return (false);
2107     }                           /* on error */
2108     
2109     
2110     /* Allocate enough room for all the symbols in cached form */
2111     cached_area =
2112       (coff_symbol_type *)
2113         bfd_alloc(abfd, (size_t) (bfd_get_symcount(abfd) * sizeof(coff_symbol_type)));
2114     
2115     if (cached_area == NULL) {
2116       bfd_error = no_memory;
2117       return false;
2118     }                           /* on error */
2119     table_ptr =
2120       (unsigned int *)
2121         bfd_alloc(abfd, (size_t) (bfd_get_symcount(abfd) * sizeof(unsigned int)));
2122     
2123     if (table_ptr == NULL) {
2124       bfd_error = no_memory;
2125       return false;
2126     } else {
2127       coff_symbol_type *dst = cached_area;
2128       unsigned int    last_native_index = bfd_get_symcount(abfd);
2129       unsigned int    this_index = 0;
2130       while (this_index < last_native_index) {
2131         struct internal_syment         *src = native_symbols + this_index;
2132         table_ptr[this_index] = number_of_symbols;
2133         dst->symbol.the_bfd = abfd;
2134         
2135         dst->symbol.name = (char *)(src->_n._n_n._n_offset);
2136         /*
2137           We use the native name field to point to the cached field
2138             */
2139         src->_n._n_n._n_zeroes = (int) dst;
2140         dst->symbol.section = section_from_bfd_index(abfd,
2141                                                      src->n_scnum);
2142         switch (src->n_sclass) {
2143 #ifdef I960
2144         case C_LEAFEXT:
2145 #if 0
2146           dst->symbol.value = src->n_value - dst->symbol.section->vma;
2147           dst->symbol.flags = BSF_EXPORT | BSF_GLOBAL;
2148           dst->symbol.flags |= BSF_NOT_AT_END;
2149 #endif
2150           /* Fall through to next case */
2151           
2152 #endif
2153           
2154         case C_EXT:
2155           if ((src->n_scnum) == 0) {
2156             if ((src->n_value) == 0) {
2157               dst->symbol.flags = BSF_UNDEFINED;
2158               dst->symbol.value= 0;
2159             }
2160             else {
2161               dst->symbol.flags = BSF_FORT_COMM;
2162               dst->symbol.value = (src->n_value);
2163             }
2164           }
2165           else {
2166             /*
2167               Base the value as an index from the base of the
2168                 section
2169                   */
2170             if (dst->symbol.section == (asection *) NULL) {
2171               dst->symbol.flags = BSF_EXPORT | BSF_GLOBAL | BSF_ABSOLUTE;
2172               dst->symbol.value = src->n_value;
2173             }
2174             else {
2175               dst->symbol.flags = BSF_EXPORT | BSF_GLOBAL;
2176               dst->symbol.value = src->n_value - dst->symbol.section->vma;
2177             }
2178             if (ISFCN((src->n_type))) {
2179               /*
2180                 A function ext does not go at the end of a file
2181                   */
2182               dst->symbol.flags |= BSF_NOT_AT_END;
2183             }
2184           }
2185           
2186           break;
2187         case C_STAT:                    /* static                        */
2188 #ifdef I960
2189         case C_LEAFSTAT:                /* static leaf procedure        */
2190 #endif
2191         case C_LABEL:                   /* label                         */
2192           dst->symbol.flags = BSF_LOCAL;
2193           /*
2194             Base the value as an index from the base of the section
2195               */
2196           dst->symbol.value = (src->n_value) - dst->symbol.section->vma;
2197           break;
2198           
2199         case C_MOS:                     /* member of structure   */
2200         case C_EOS:                     /* end of structure              */
2201         case C_REGPARM:                 /* register parameter            */
2202         case C_REG:                     /* register variable             */
2203 #ifdef C_AUTOARG
2204         case C_AUTOARG:                 /* 960-specific storage class */
2205 #endif
2206         case C_TPDEF:                   /* type definition               */
2207           
2208         case C_ARG:
2209         case C_AUTO:                    /* automatic variable */
2210         case C_FIELD:                   /* bit field */
2211         case C_ENTAG:                   /* enumeration tag               */
2212         case C_MOE:                     /* member of enumeration         */
2213         case C_MOU:                     /* member of union               */
2214         case C_UNTAG:                   /* union tag                     */
2215           
2216           dst->symbol.flags = BSF_DEBUGGING;
2217           dst->symbol.value = (src->n_value);
2218           break;
2219           
2220         case C_FILE:                    /* file name                     */
2221         case C_STRTAG:                  /* structure tag                 */
2222           dst->symbol.flags = BSF_DEBUGGING;
2223           dst->symbol.value = (src->n_value);
2224           
2225           break;
2226         case C_BLOCK:                   /* ".bb" or ".eb"                */
2227         case C_FCN:                     /* ".bf" or ".ef"                */
2228           dst->symbol.flags = BSF_LOCAL;
2229           /*
2230             Base the value as an index from the base of the section
2231               */
2232           dst->symbol.value = (src->n_value) - dst->symbol.section->vma;
2233           
2234           break;
2235         case C_EFCN:                    /* physical end of function      */
2236         case C_NULL:
2237         case C_EXTDEF:                  /* external definition           */
2238         case C_ULABEL:                  /* undefined label               */
2239         case C_USTATIC:                 /* undefined static              */
2240         case C_LINE:                    /* line # reformatted as symbol table entry */
2241         case C_ALIAS:                   /* duplicate tag                 */
2242         case C_HIDDEN:                  /* ext symbol in dmert public lib */
2243           
2244         default:
2245           
2246           abort();
2247           dst->symbol.flags = BSF_DEBUGGING;
2248           dst->symbol.value = (src->n_value);
2249           
2250           break;
2251         }
2252         
2253         BFD_ASSERT(dst->symbol.flags != 0);
2254         
2255         dst->native = src;
2256         
2257         dst->symbol.udata = 0;
2258         dst->lineno = (alent *) NULL;
2259         this_index += (src->n_numaux) + 1;
2260         dst++;
2261         number_of_symbols++;
2262       }                         /* walk the native symtab */
2263     }                           /* bfdize the native symtab */
2264     
2265     obj_symbols(abfd) = cached_area;
2266     obj_raw_syments(abfd) = native_symbols;
2267     
2268     bfd_get_symcount(abfd) = number_of_symbols;
2269     obj_convert(abfd) = table_ptr;
2270     /* Slurp the line tables for each section too */
2271       {
2272         asection       *p;
2273         p = abfd->sections;
2274         while (p) {
2275           coff_slurp_line_table(abfd, p);
2276           p = p->next;
2277         }
2278       }
2279     return true;
2280   }                             /* coff_slurp_symbol_table() */
2281
2282 static unsigned int
2283 coff_get_symtab_upper_bound(abfd)
2284 bfd            *abfd;
2285   {
2286     if (!coff_slurp_symbol_table(abfd))
2287       return 0;
2288     
2289     return (bfd_get_symcount(abfd) + 1) * (sizeof(coff_symbol_type *));
2290   }
2291
2292
2293 static unsigned int
2294 coff_get_symtab(abfd, alocation)
2295 bfd            *abfd;
2296 asymbol       **alocation;
2297   {
2298     unsigned int    counter = 0;
2299     coff_symbol_type *symbase;
2300     coff_symbol_type **location = (coff_symbol_type **) (alocation);
2301     if (!coff_slurp_symbol_table(abfd))
2302       return 0;
2303     
2304     for (symbase = obj_symbols(abfd); counter++ < bfd_get_symcount(abfd);)
2305       *(location++) = symbase++;
2306     *location++ = 0;
2307     return bfd_get_symcount(abfd);
2308   }
2309
2310 static unsigned int
2311 coff_get_reloc_upper_bound(abfd, asect)
2312 bfd            *abfd;
2313 sec_ptr         asect;
2314   {
2315     if (bfd_get_format(abfd) != bfd_object) {
2316       bfd_error = invalid_operation;
2317       return 0;
2318     }
2319     return (asect->reloc_count + 1) * sizeof(arelent *);
2320   }
2321
2322 static          boolean
2323 DEFUN(coff_slurp_reloc_table,(abfd, asect, symbols),
2324       bfd            *abfd AND
2325       sec_ptr         asect AND
2326       asymbol       **symbols)
2327   {
2328     RELOC   *native_relocs;
2329     arelent        *reloc_cache;
2330     if (asect->relocation)
2331       return true;
2332     if (asect->reloc_count == 0)
2333       return true;
2334     if (!coff_slurp_symbol_table(abfd))
2335       return false;
2336     native_relocs =
2337       (RELOC *) buy_and_read(abfd,
2338                              asect->rel_filepos,
2339                              SEEK_SET,
2340                              (size_t) (RELSZ *
2341                                        asect->reloc_count));
2342     reloc_cache = (arelent *)
2343       bfd_alloc(abfd, (size_t) (asect->reloc_count * sizeof(arelent)));
2344     
2345     if (reloc_cache == NULL) {
2346       bfd_error = no_memory;
2347       return false;
2348     } {                         /* on error */
2349       arelent        *cache_ptr;
2350       RELOC   *src;
2351       for (cache_ptr = reloc_cache,
2352            src = native_relocs;
2353            cache_ptr < reloc_cache + asect->reloc_count;
2354            cache_ptr++,
2355            src++) {
2356         struct internal_reloc dst;
2357         asymbol        *ptr;
2358         bfd_swap_reloc_in(abfd, src, &dst);
2359         dst.r_symndx += obj_symbol_slew(abfd);
2360         cache_ptr->sym_ptr_ptr = symbols + obj_convert(abfd)[dst.r_symndx];
2361         
2362         ptr = *(cache_ptr->sym_ptr_ptr);
2363         cache_ptr->address = dst.r_vaddr;
2364         /*
2365           The symbols definitions that we have read in have been
2366           relocated as if their sections started at 0. But the offsets
2367           refering to the symbols in the raw data have not been
2368           modified, so we have to have a negative addend to compensate.
2369           
2370           Note that symbols which used to be common must be left alone
2371           */
2372         
2373         if (ptr->the_bfd == abfd 
2374             && ptr->section != (asection *) NULL 
2375             && ((ptr->flags & BSF_OLD_COMMON)== 0)) 
2376             {
2377               cache_ptr->addend = -(ptr->section->vma + ptr->value);
2378             }
2379         else {
2380           cache_ptr->addend = 0;
2381         }
2382         
2383         cache_ptr->address -= asect->vma;
2384         
2385         cache_ptr->section = (asection *) NULL;
2386         
2387 #if I960
2388         cache_ptr->howto = howto_table + dst.r_type;
2389 #endif
2390 #if M68
2391         cache_ptr->howto = howto_table + dst.r_type - R_RELBYTE;
2392 #endif
2393 #if M88
2394         if (dst.r_type >= R_PCR16L && dst.r_type <= R_VRT32) {
2395           cache_ptr->howto = howto_table + dst.r_type - R_PCR16L;
2396           cache_ptr->addend += dst.r_offset << 16;
2397         }
2398         else {
2399           BFD_ASSERT(0);
2400         }
2401 #endif
2402         
2403       }
2404       
2405     }
2406     
2407     asect->relocation = reloc_cache;
2408     return true;
2409   }
2410
2411
2412 /* This is stupid.  This function should be a boolean predicate */
2413 static unsigned int
2414 coff_canonicalize_reloc(abfd, section, relptr, symbols)
2415 bfd            *abfd;
2416 sec_ptr         section;
2417 arelent       **relptr;
2418 asymbol       **symbols;
2419   {
2420     arelent        *tblptr = section->relocation;
2421     unsigned int    count = 0;
2422     if (!(tblptr || coff_slurp_reloc_table(abfd, section, symbols)))
2423       return 0;
2424     tblptr = section->relocation;
2425     if (!tblptr)
2426       return 0;
2427     
2428     for (; count++ < section->reloc_count;)
2429       *relptr++ = tblptr++;
2430     
2431     *relptr = 0;
2432     
2433     return section->reloc_count;
2434   }
2435
2436
2437 /*
2438 provided a bfd, a section and an offset into the section, calculate and
2439 return the name of the source file and the line nearest to the wanted
2440 location.
2441 */
2442
2443 static          boolean
2444 DEFUN(coff_find_nearest_line,(abfd,
2445                               section,
2446                               symbols,
2447                               offset,
2448                               filename_ptr,
2449                               functionname_ptr,
2450                               line_ptr),
2451       bfd            *abfd AND
2452       asection       *section AND
2453       asymbol       **symbols AND
2454       bfd_vma         offset AND
2455       CONST char      **filename_ptr AND
2456       CONST char       **functionname_ptr AND
2457       unsigned int   *line_ptr)
2458 {
2459   static bfd     *cache_abfd;
2460   static asection *cache_section;
2461   static bfd_vma  cache_offset;
2462   static unsigned int cache_i;
2463   static alent   *cache_l;
2464     
2465   unsigned int    i = 0;
2466   struct icofdata *cof = obj_icof(abfd);
2467   /* Run through the raw syments if available */
2468   struct internal_syment         *p;
2469   alent          *l;
2470   unsigned int    line_base = 0;
2471     
2472     
2473   *filename_ptr = 0;
2474   *functionname_ptr = 0;
2475   *line_ptr = 0;
2476     
2477   /* Don't try and find line numbers in a non coff file */
2478   if (abfd->xvec->flavour != bfd_target_coff_flavour_enum)
2479     return false;
2480     
2481   if (cof == (struct icofdata *)NULL)
2482     return false;
2483     
2484   p = cof->raw_syments;
2485   /*
2486     I don't know for sure what's right, but this isn't it. First off, an
2487     object file may not have any C_FILE's in it.  After
2488     get_normalized_symtab(), it should have at least 1, the one I put
2489     there, but otherwise, all bets are off.  Point #2, the first C_FILE
2490     isn't necessarily the right C_FILE because any given object may have
2491     many.  I think you'll have to track sections as they coelesce in order
2492     to find the C_STAT symbol for this section. Then you'll have to work
2493     backwards to find the previous C_FILE, or choke if you get to a C_STAT
2494     for the same kind of section.  That will mean that the original object
2495     file didn't have a C_FILE. xoxorich.
2496     */
2497     
2498 #ifdef WEREBEINGPEDANTIC
2499   return false;
2500 #endif
2501     
2502   for (i = 0; i < cof->raw_syment_count; i++) {
2503     if (p->n_sclass == C_FILE) {
2504       /* File name is embeded in auxent */
2505       /*
2506         This isn't right.  The fname should probably be normalized
2507         during get_normalized_symtab().  In any case, what was here
2508         wasn't right because a SYMENT.n_name isn't an
2509         AUXENT.x_file.x_fname. xoxorich.
2510         */
2511         
2512       *filename_ptr = ((AUXENT *) (p + 1))->x_file.x_fname;
2513       break;
2514     }
2515     p += 1 +  p->n_numaux;
2516   }
2517   /* Now wander though the raw linenumbers of the section */
2518   /*
2519     If this is the same bfd as we were previously called with and this is
2520     the same section, and the offset we want is further down then we can
2521     prime the lookup loop
2522     */
2523   if (abfd == cache_abfd &&
2524       section == cache_section &&
2525       offset >= cache_offset) {
2526     i = cache_i;
2527     l = cache_l;
2528   }
2529   else {
2530     i = 0;
2531     l = section->lineno;
2532   }
2533     
2534   for (; i < section->lineno_count; i++) {
2535     if (l->line_number == 0) {
2536       /* Get the symbol this line number points at */
2537       coff_symbol_type *coff = (coff_symbol_type *) (l->u.sym);
2538       *functionname_ptr = coff->symbol.name;
2539       if (coff->native) {
2540         struct internal_syment  *s = coff->native;
2541         s = s + 1 + s->n_numaux;
2542         /*
2543           S should now point to the .bf of the function
2544           */
2545         if (s->n_numaux) {
2546           /*
2547             The linenumber is stored in the auxent
2548             */
2549           union internal_auxent   *a = (union internal_auxent *) (s + 1);
2550           line_base = a->x_sym.x_misc.x_lnsz.x_lnno;
2551         }
2552       }
2553     }
2554     else {
2555       if (l->u.offset > offset)
2556         break;
2557       *line_ptr = l->line_number + line_base + 1;
2558     }
2559     l++;
2560   }
2561     
2562   cache_abfd = abfd;
2563   cache_section = section;
2564   cache_offset = offset;
2565   cache_i = i;
2566   cache_l = l;
2567   return true;
2568 }
2569
2570 #ifdef GNU960
2571 file_ptr
2572 coff_sym_filepos(abfd)
2573 bfd *abfd;
2574   {
2575     return obj_sym_filepos(abfd);
2576   }
2577 #endif
2578
2579
2580 static int 
2581 DEFUN(coff_sizeof_headers,(abfd, reloc),
2582       bfd *abfd AND
2583       boolean reloc)
2584   {
2585     size_t size;
2586     
2587     if (reloc == false) {
2588       size = FILHSZ + AOUTSZ;
2589     }
2590     else {
2591       size = FILHSZ;
2592     }
2593     
2594     size +=  abfd->section_count * SCNHSZ;
2595     return size;
2596   }
2597
2598
2599 #define coff_core_file_failing_command  _bfd_dummy_core_file_failing_command
2600 #define coff_core_file_failing_signal   _bfd_dummy_core_file_failing_signal
2601 #define coff_core_file_matches_executable_p     _bfd_dummy_core_file_matches_executable_p
2602 #define coff_slurp_armap                bfd_slurp_coff_armap
2603 #define coff_slurp_extended_name_table  _bfd_slurp_extended_name_table
2604 #define coff_truncate_arname            bfd_dont_truncate_arname
2605 #define coff_openr_next_archived_file   bfd_generic_openr_next_archived_file
2606 #define coff_generic_stat_arch_elt      bfd_generic_stat_arch_elt
2607 #define coff_get_section_contents       bfd_generic_get_section_contents
2608 #define coff_close_and_cleanup          bfd_generic_close_and_cleanup