* libbfd.c (bfd_malloc, bfd_realloc): New functions.
[external/binutils.git] / bfd / peicode.h
1 /* Support for the generic parts of most COFF variants, for BFD.
2    Copyright 1995 Free Software Foundation, Inc.
3    Written by Cygnus Support.
4
5 This file is part of BFD, the Binary File Descriptor library.
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
20
21 /*
22 Most of this hacked by  Steve Chamberlain,
23                         sac@cygnus.com
24 */
25
26
27
28 #define coff_bfd_print_private_bfd_data pe_print_private_bfd_data
29 #define coff_mkobject pe_mkobject
30 #define coff_mkobject_hook pe_mkobject_hook
31
32 #ifndef GET_FCN_LNNOPTR
33 #define GET_FCN_LNNOPTR(abfd, ext) \
34      bfd_h_get_32(abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_fcn.x_lnnoptr)
35 #endif
36
37 #ifndef GET_FCN_ENDNDX
38 #define GET_FCN_ENDNDX(abfd, ext)  \
39         bfd_h_get_32(abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_fcn.x_endndx)
40 #endif
41
42 #ifndef PUT_FCN_LNNOPTR
43 #define PUT_FCN_LNNOPTR(abfd, in, ext)  bfd_h_put_32(abfd,  in, (bfd_byte *) ext->x_sym.x_fcnary.x_fcn.x_lnnoptr)
44 #endif
45 #ifndef PUT_FCN_ENDNDX
46 #define PUT_FCN_ENDNDX(abfd, in, ext) bfd_h_put_32(abfd, in, (bfd_byte *) ext->x_sym.x_fcnary.x_fcn.x_endndx)
47 #endif
48 #ifndef GET_LNSZ_LNNO
49 #define GET_LNSZ_LNNO(abfd, ext) bfd_h_get_16(abfd, (bfd_byte *) ext->x_sym.x_misc.x_lnsz.x_lnno)
50 #endif
51 #ifndef GET_LNSZ_SIZE
52 #define GET_LNSZ_SIZE(abfd, ext) bfd_h_get_16(abfd, (bfd_byte *) ext->x_sym.x_misc.x_lnsz.x_size)
53 #endif
54 #ifndef PUT_LNSZ_LNNO
55 #define PUT_LNSZ_LNNO(abfd, in, ext) bfd_h_put_16(abfd, in, (bfd_byte *)ext->x_sym.x_misc.x_lnsz.x_lnno)
56 #endif
57 #ifndef PUT_LNSZ_SIZE
58 #define PUT_LNSZ_SIZE(abfd, in, ext) bfd_h_put_16(abfd, in, (bfd_byte*) ext->x_sym.x_misc.x_lnsz.x_size)
59 #endif
60 #ifndef GET_SCN_SCNLEN
61 #define GET_SCN_SCNLEN(abfd,  ext) bfd_h_get_32(abfd, (bfd_byte *) ext->x_scn.x_scnlen)
62 #endif
63 #ifndef GET_SCN_NRELOC
64 #define GET_SCN_NRELOC(abfd,  ext) bfd_h_get_16(abfd, (bfd_byte *)ext->x_scn.x_nreloc)
65 #endif
66 #ifndef GET_SCN_NLINNO
67 #define GET_SCN_NLINNO(abfd, ext)  bfd_h_get_16(abfd, (bfd_byte *)ext->x_scn.x_nlinno)
68 #endif
69 #ifndef PUT_SCN_SCNLEN
70 #define PUT_SCN_SCNLEN(abfd,in, ext) bfd_h_put_32(abfd, in, (bfd_byte *) ext->x_scn.x_scnlen)
71 #endif
72 #ifndef PUT_SCN_NRELOC
73 #define PUT_SCN_NRELOC(abfd,in, ext) bfd_h_put_16(abfd, in, (bfd_byte *)ext->x_scn.x_nreloc)
74 #endif
75 #ifndef PUT_SCN_NLINNO
76 #define PUT_SCN_NLINNO(abfd,in, ext)  bfd_h_put_16(abfd,in, (bfd_byte  *) ext->x_scn.x_nlinno)
77 #endif
78 #ifndef GET_LINENO_LNNO
79 #define GET_LINENO_LNNO(abfd, ext) bfd_h_get_16(abfd, (bfd_byte *) (ext->l_lnno));
80 #endif
81 #ifndef PUT_LINENO_LNNO
82 #define PUT_LINENO_LNNO(abfd,val, ext) bfd_h_put_16(abfd,val,  (bfd_byte *) (ext->l_lnno));
83 #endif
84
85 /* The f_symptr field in the filehdr is sometimes 64 bits.  */
86 #ifndef GET_FILEHDR_SYMPTR
87 #define GET_FILEHDR_SYMPTR bfd_h_get_32
88 #endif
89 #ifndef PUT_FILEHDR_SYMPTR
90 #define PUT_FILEHDR_SYMPTR bfd_h_put_32
91 #endif
92
93 /* Some fields in the aouthdr are sometimes 64 bits.  */
94 #ifndef GET_AOUTHDR_TSIZE
95 #define GET_AOUTHDR_TSIZE bfd_h_get_32
96 #endif
97 #ifndef PUT_AOUTHDR_TSIZE
98 #define PUT_AOUTHDR_TSIZE bfd_h_put_32
99 #endif
100 #ifndef GET_AOUTHDR_DSIZE
101 #define GET_AOUTHDR_DSIZE bfd_h_get_32
102 #endif
103 #ifndef PUT_AOUTHDR_DSIZE
104 #define PUT_AOUTHDR_DSIZE bfd_h_put_32
105 #endif
106 #ifndef GET_AOUTHDR_BSIZE
107 #define GET_AOUTHDR_BSIZE bfd_h_get_32
108 #endif
109 #ifndef PUT_AOUTHDR_BSIZE
110 #define PUT_AOUTHDR_BSIZE bfd_h_put_32
111 #endif
112 #ifndef GET_AOUTHDR_ENTRY
113 #define GET_AOUTHDR_ENTRY bfd_h_get_32
114 #endif
115 #ifndef PUT_AOUTHDR_ENTRY
116 #define PUT_AOUTHDR_ENTRY bfd_h_put_32
117 #endif
118 #ifndef GET_AOUTHDR_TEXT_START
119 #define GET_AOUTHDR_TEXT_START bfd_h_get_32
120 #endif
121 #ifndef PUT_AOUTHDR_TEXT_START
122 #define PUT_AOUTHDR_TEXT_START bfd_h_put_32
123 #endif
124 #ifndef GET_AOUTHDR_DATA_START
125 #define GET_AOUTHDR_DATA_START bfd_h_get_32
126 #endif
127 #ifndef PUT_AOUTHDR_DATA_START
128 #define PUT_AOUTHDR_DATA_START bfd_h_put_32
129 #endif
130
131 /* Some fields in the scnhdr are sometimes 64 bits.  */
132 #ifndef GET_SCNHDR_PADDR
133 #define GET_SCNHDR_PADDR bfd_h_get_32
134 #endif
135 #ifndef PUT_SCNHDR_PADDR
136 #define PUT_SCNHDR_PADDR bfd_h_put_32
137 #endif
138 #ifndef GET_SCNHDR_VADDR
139 #define GET_SCNHDR_VADDR bfd_h_get_32
140 #endif
141 #ifndef PUT_SCNHDR_VADDR
142 #define PUT_SCNHDR_VADDR bfd_h_put_32
143 #endif
144 #ifndef GET_SCNHDR_SIZE
145 #define GET_SCNHDR_SIZE bfd_h_get_32
146 #endif
147 #ifndef PUT_SCNHDR_SIZE
148 #define PUT_SCNHDR_SIZE bfd_h_put_32
149 #endif
150 #ifndef GET_SCNHDR_SCNPTR
151 #define GET_SCNHDR_SCNPTR bfd_h_get_32
152 #endif
153 #ifndef PUT_SCNHDR_SCNPTR
154 #define PUT_SCNHDR_SCNPTR bfd_h_put_32
155 #endif
156 #ifndef GET_SCNHDR_RELPTR
157 #define GET_SCNHDR_RELPTR bfd_h_get_32
158 #endif
159 #ifndef PUT_SCNHDR_RELPTR
160 #define PUT_SCNHDR_RELPTR bfd_h_put_32
161 #endif
162 #ifndef GET_SCNHDR_LNNOPTR
163 #define GET_SCNHDR_LNNOPTR bfd_h_get_32
164 #endif
165 #ifndef PUT_SCNHDR_LNNOPTR
166 #define PUT_SCNHDR_LNNOPTR bfd_h_put_32
167 #endif
168
169
170
171 /**********************************************************************/
172
173 static void
174 coff_swap_reloc_in (abfd, src, dst)
175      bfd *abfd;
176      PTR src;
177      PTR dst;
178 {
179   RELOC *reloc_src = (RELOC *) src;
180   struct internal_reloc *reloc_dst = (struct internal_reloc *) dst;
181
182   reloc_dst->r_vaddr = bfd_h_get_32(abfd, (bfd_byte *)reloc_src->r_vaddr);
183   reloc_dst->r_symndx = bfd_h_get_signed_32(abfd, (bfd_byte *) reloc_src->r_symndx);
184
185   reloc_dst->r_type = bfd_h_get_16(abfd, (bfd_byte *) reloc_src->r_type);
186
187 #ifdef SWAP_IN_RELOC_OFFSET
188   reloc_dst->r_offset = SWAP_IN_RELOC_OFFSET(abfd,
189                                              (bfd_byte *) reloc_src->r_offset);
190 #endif
191 }
192
193
194 static unsigned int
195 coff_swap_reloc_out (abfd, src, dst)
196      bfd       *abfd;
197      PTR        src;
198      PTR        dst;
199 {
200   struct internal_reloc *reloc_src = (struct internal_reloc *)src;
201   struct external_reloc *reloc_dst = (struct external_reloc *)dst;
202   bfd_h_put_32(abfd, reloc_src->r_vaddr, (bfd_byte *) reloc_dst->r_vaddr);
203   bfd_h_put_32(abfd, reloc_src->r_symndx, (bfd_byte *) reloc_dst->r_symndx);
204
205   bfd_h_put_16(abfd, reloc_src->r_type, (bfd_byte *)
206                reloc_dst->r_type);
207
208 #ifdef SWAP_OUT_RELOC_OFFSET
209   SWAP_OUT_RELOC_OFFSET(abfd,
210                         reloc_src->r_offset,
211                         (bfd_byte *) reloc_dst->r_offset);
212 #endif
213 #ifdef SWAP_OUT_RELOC_EXTRA
214   SWAP_OUT_RELOC_EXTRA(abfd,reloc_src, reloc_dst);
215 #endif
216   return sizeof(struct external_reloc);
217 }
218
219
220 static void
221 coff_swap_filehdr_in (abfd, src, dst)
222      bfd            *abfd;
223      PTR             src;
224      PTR             dst;
225 {
226   FILHDR *filehdr_src = (FILHDR *) src;
227   struct internal_filehdr *filehdr_dst = (struct internal_filehdr *) dst;
228   filehdr_dst->f_magic = bfd_h_get_16(abfd, (bfd_byte *) filehdr_src->f_magic);
229   filehdr_dst->f_nscns = bfd_h_get_16(abfd, (bfd_byte *)filehdr_src-> f_nscns);
230   filehdr_dst->f_timdat = bfd_h_get_32(abfd, (bfd_byte *)filehdr_src-> f_timdat);
231
232   filehdr_dst->f_nsyms = bfd_h_get_32(abfd, (bfd_byte *)filehdr_src-> f_nsyms);
233   filehdr_dst->f_flags = bfd_h_get_16(abfd, (bfd_byte *)filehdr_src-> f_flags);
234   filehdr_dst->f_symptr = bfd_h_get_32 (abfd, (bfd_byte *) filehdr_src->f_symptr);
235
236   /* Other people's tools sometimes generate headers
237      with an nsyms but a zero symptr. */
238   if (filehdr_dst->f_nsyms && filehdr_dst->f_symptr)
239     {
240       filehdr_dst->f_flags |= HAS_SYMS;
241     }
242   else 
243     {
244       filehdr_dst->f_symptr = 0;
245       filehdr_dst->f_nsyms = 0;
246       filehdr_dst->f_flags &= ~HAS_SYMS;
247     }
248
249   filehdr_dst->f_opthdr = bfd_h_get_16(abfd, 
250                                        (bfd_byte *)filehdr_src-> f_opthdr);
251 }
252
253 #ifdef COFF_IMAGE_WITH_PE
254
255 static  unsigned int
256 coff_swap_filehdr_out (abfd, in, out)
257      bfd       *abfd;
258      PTR        in;
259      PTR        out;
260 {
261   int idx;
262   struct internal_filehdr *filehdr_in = (struct internal_filehdr *)in;
263   FILHDR *filehdr_out = (FILHDR *)out;
264
265   if (pe_data (abfd)->has_reloc_section)
266     filehdr_in->f_flags &= ~F_RELFLG;
267
268   if (pe_data (abfd)->dll)
269     filehdr_in->f_flags |= F_DLL;
270
271   filehdr_in->pe.e_magic    = DOSMAGIC;
272   filehdr_in->pe.e_cblp     = 0x90;
273   filehdr_in->pe.e_cp       = 0x3;
274   filehdr_in->pe.e_crlc     = 0x0;
275   filehdr_in->pe.e_cparhdr  = 0x4;
276   filehdr_in->pe.e_minalloc = 0x0;
277   filehdr_in->pe.e_maxalloc = 0xffff;
278   filehdr_in->pe.e_ss       = 0x0;
279   filehdr_in->pe.e_sp       = 0xb8;
280   filehdr_in->pe.e_csum     = 0x0;
281   filehdr_in->pe.e_ip       = 0x0;
282   filehdr_in->pe.e_cs       = 0x0;
283   filehdr_in->pe.e_lfarlc   = 0x40;
284   filehdr_in->pe.e_ovno     = 0x0;
285
286   for (idx=0; idx < 4; idx++)
287     filehdr_in->pe.e_res[idx] = 0x0;
288
289   filehdr_in->pe.e_oemid   = 0x0;
290   filehdr_in->pe.e_oeminfo = 0x0;
291
292   for (idx=0; idx < 10; idx++)
293     filehdr_in->pe.e_res2[idx] = 0x0;
294
295   filehdr_in->pe.e_lfanew = 0x80;
296
297   /* this next collection of data are mostly just characters.  It appears
298      to be constant within the headers put on NT exes */
299   filehdr_in->pe.dos_message[0]  = 0x0eba1f0e;
300   filehdr_in->pe.dos_message[1]  = 0xcd09b400;
301   filehdr_in->pe.dos_message[2]  = 0x4c01b821;
302   filehdr_in->pe.dos_message[3]  = 0x685421cd;
303   filehdr_in->pe.dos_message[4]  = 0x70207369;
304   filehdr_in->pe.dos_message[5]  = 0x72676f72;
305   filehdr_in->pe.dos_message[6]  = 0x63206d61;
306   filehdr_in->pe.dos_message[7]  = 0x6f6e6e61;
307   filehdr_in->pe.dos_message[8]  = 0x65622074;
308   filehdr_in->pe.dos_message[9]  = 0x6e757220;
309   filehdr_in->pe.dos_message[10] = 0x206e6920;
310   filehdr_in->pe.dos_message[11] = 0x20534f44;
311   filehdr_in->pe.dos_message[12] = 0x65646f6d;
312   filehdr_in->pe.dos_message[13] = 0x0a0d0d2e;
313   filehdr_in->pe.dos_message[14] = 0x24;
314   filehdr_in->pe.dos_message[15] = 0x0;
315   filehdr_in->pe.nt_signature = NT_SIGNATURE;
316
317
318
319   bfd_h_put_16(abfd, filehdr_in->f_magic, (bfd_byte *) filehdr_out->f_magic);
320   bfd_h_put_16(abfd, filehdr_in->f_nscns, (bfd_byte *) filehdr_out->f_nscns);
321
322   bfd_h_put_32(abfd, time (0), (bfd_byte *) filehdr_out->f_timdat);
323   PUT_FILEHDR_SYMPTR (abfd, (bfd_vma) filehdr_in->f_symptr,
324                       (bfd_byte *) filehdr_out->f_symptr);
325   bfd_h_put_32(abfd, filehdr_in->f_nsyms, (bfd_byte *) filehdr_out->f_nsyms);
326   bfd_h_put_16(abfd, filehdr_in->f_opthdr, (bfd_byte *) filehdr_out->f_opthdr);
327   bfd_h_put_16(abfd, filehdr_in->f_flags, (bfd_byte *) filehdr_out->f_flags);
328
329   /* put in extra dos header stuff.  This data remains essentially
330      constant, it just has to be tacked on to the beginning of all exes 
331      for NT */
332   bfd_h_put_16(abfd, filehdr_in->pe.e_magic, (bfd_byte *) filehdr_out->e_magic);
333   bfd_h_put_16(abfd, filehdr_in->pe.e_cblp, (bfd_byte *) filehdr_out->e_cblp);
334   bfd_h_put_16(abfd, filehdr_in->pe.e_cp, (bfd_byte *) filehdr_out->e_cp);
335   bfd_h_put_16(abfd, filehdr_in->pe.e_crlc, (bfd_byte *) filehdr_out->e_crlc);
336   bfd_h_put_16(abfd, filehdr_in->pe.e_cparhdr, 
337                (bfd_byte *) filehdr_out->e_cparhdr);
338   bfd_h_put_16(abfd, filehdr_in->pe.e_minalloc, 
339                (bfd_byte *) filehdr_out->e_minalloc);
340   bfd_h_put_16(abfd, filehdr_in->pe.e_maxalloc, 
341                (bfd_byte *) filehdr_out->e_maxalloc);
342   bfd_h_put_16(abfd, filehdr_in->pe.e_ss, (bfd_byte *) filehdr_out->e_ss);
343   bfd_h_put_16(abfd, filehdr_in->pe.e_sp, (bfd_byte *) filehdr_out->e_sp);
344   bfd_h_put_16(abfd, filehdr_in->pe.e_csum, (bfd_byte *) filehdr_out->e_csum);
345   bfd_h_put_16(abfd, filehdr_in->pe.e_ip, (bfd_byte *) filehdr_out->e_ip);
346   bfd_h_put_16(abfd, filehdr_in->pe.e_cs, (bfd_byte *) filehdr_out->e_cs);
347   bfd_h_put_16(abfd, filehdr_in->pe.e_lfarlc, (bfd_byte *) filehdr_out->e_lfarlc);
348   bfd_h_put_16(abfd, filehdr_in->pe.e_ovno, (bfd_byte *) filehdr_out->e_ovno);
349   {
350     int idx;
351     for (idx=0; idx < 4; idx++)
352       bfd_h_put_16(abfd, filehdr_in->pe.e_res[idx], 
353                    (bfd_byte *) filehdr_out->e_res[idx]);
354   }
355   bfd_h_put_16(abfd, filehdr_in->pe.e_oemid, (bfd_byte *) filehdr_out->e_oemid);
356   bfd_h_put_16(abfd, filehdr_in->pe.e_oeminfo,
357                (bfd_byte *) filehdr_out->e_oeminfo);
358   {
359     int idx;
360     for (idx=0; idx < 10; idx++)
361       bfd_h_put_16(abfd, filehdr_in->pe.e_res2[idx],
362                    (bfd_byte *) filehdr_out->e_res2[idx]);
363   }
364   bfd_h_put_32(abfd, filehdr_in->pe.e_lfanew, (bfd_byte *) filehdr_out->e_lfanew);
365
366   {
367     int idx;
368     for (idx=0; idx < 16; idx++)
369       bfd_h_put_32(abfd, filehdr_in->pe.dos_message[idx],
370                    (bfd_byte *) filehdr_out->dos_message[idx]);
371   }
372
373   /* also put in the NT signature */
374   bfd_h_put_32(abfd, filehdr_in->pe.nt_signature, 
375                (bfd_byte *) filehdr_out->nt_signature);
376
377
378
379
380   return sizeof(FILHDR);
381 }
382 #else
383
384 static  unsigned int
385 coff_swap_filehdr_out (abfd, in, out)
386      bfd       *abfd;
387      PTR        in;
388      PTR        out;
389 {
390   struct internal_filehdr *filehdr_in = (struct internal_filehdr *)in;
391   FILHDR *filehdr_out = (FILHDR *)out;
392
393   bfd_h_put_16(abfd, filehdr_in->f_magic, (bfd_byte *) filehdr_out->f_magic);
394   bfd_h_put_16(abfd, filehdr_in->f_nscns, (bfd_byte *) filehdr_out->f_nscns);
395   bfd_h_put_32(abfd, filehdr_in->f_timdat, (bfd_byte *) filehdr_out->f_timdat);
396   PUT_FILEHDR_SYMPTR (abfd, (bfd_vma) filehdr_in->f_symptr,
397                       (bfd_byte *) filehdr_out->f_symptr);
398   bfd_h_put_32(abfd, filehdr_in->f_nsyms, (bfd_byte *) filehdr_out->f_nsyms);
399   bfd_h_put_16(abfd, filehdr_in->f_opthdr, (bfd_byte *) filehdr_out->f_opthdr);
400   bfd_h_put_16(abfd, filehdr_in->f_flags, (bfd_byte *) filehdr_out->f_flags);
401
402   return sizeof(FILHDR);
403 }
404
405 #endif
406
407
408 static void
409 coff_swap_sym_in (abfd, ext1, in1)
410      bfd            *abfd;
411      PTR ext1;
412      PTR in1;
413 {
414   SYMENT *ext = (SYMENT *)ext1;
415   struct internal_syment      *in = (struct internal_syment *)in1;
416
417   if( ext->e.e_name[0] == 0) {
418     in->_n._n_n._n_zeroes = 0;
419     in->_n._n_n._n_offset = bfd_h_get_32(abfd, (bfd_byte *) ext->e.e.e_offset);
420   }
421   else {
422 #if SYMNMLEN != E_SYMNMLEN
423     -> Error, we need to cope with truncating or extending SYMNMLEN!;
424 #else
425     memcpy(in->_n._n_name, ext->e.e_name, SYMNMLEN);
426 #endif
427   }
428
429   in->n_value = bfd_h_get_32(abfd, (bfd_byte *) ext->e_value); 
430   in->n_scnum = bfd_h_get_16(abfd, (bfd_byte *) ext->e_scnum);
431   if (sizeof(ext->e_type) == 2){
432     in->n_type = bfd_h_get_16(abfd, (bfd_byte *) ext->e_type);
433   }
434   else {
435     in->n_type = bfd_h_get_32(abfd, (bfd_byte *) ext->e_type);
436   }
437   in->n_sclass = bfd_h_get_8(abfd, ext->e_sclass);
438   in->n_numaux = bfd_h_get_8(abfd, ext->e_numaux);
439
440   /* The section symbols for the .idata$ sections have class 68, which MS
441      documentation indicates is a section symbol.  The problem is that the
442      value field in the symbol is simply a copy of the .idata section's flags
443      rather than something useful.  When these symbols are encountered, change
444      the value to 0 and the section number to 1 so that they will be handled
445      somewhat correctly in the bfd code. */
446   if (in->n_sclass == 0x68) {
447     in->n_value = 0x0;
448     in->n_scnum = 1;
449     /* I have tried setting the class to 3 and using the following to set
450        the section number.  This will put the address of the pointer to the
451        string kernel32.dll at addresses 0 and 0x10 off start of idata section
452        which is not correct */
453     /*    if (strcmp (in->_n._n_name, ".idata$4") == 0) */
454     /*      in->n_scnum = 3; */
455     /*    else */
456     /*      in->n_scnum = 2; */
457   }
458
459 #ifdef coff_swap_sym_in_hook
460   coff_swap_sym_in_hook(abfd, ext1, in1);
461 #endif
462 }
463
464 static unsigned int
465 coff_swap_sym_out (abfd, inp, extp)
466      bfd       *abfd;
467      PTR        inp;
468      PTR        extp;
469 {
470   struct internal_syment *in = (struct internal_syment *)inp;
471   SYMENT *ext =(SYMENT *)extp;
472   if(in->_n._n_name[0] == 0) {
473     bfd_h_put_32(abfd, 0, (bfd_byte *) ext->e.e.e_zeroes);
474     bfd_h_put_32(abfd, in->_n._n_n._n_offset, (bfd_byte *)  ext->e.e.e_offset);
475   }
476   else {
477 #if SYMNMLEN != E_SYMNMLEN
478     -> Error, we need to cope with truncating or extending SYMNMLEN!;
479 #else
480     memcpy(ext->e.e_name, in->_n._n_name, SYMNMLEN);
481 #endif
482   }
483
484   bfd_h_put_32(abfd,  in->n_value , (bfd_byte *) ext->e_value);
485   bfd_h_put_16(abfd,  in->n_scnum , (bfd_byte *) ext->e_scnum);
486   if (sizeof(ext->e_type) == 2)
487     {
488       bfd_h_put_16(abfd,  in->n_type , (bfd_byte *) ext->e_type);
489     }
490   else
491     {
492       bfd_h_put_32(abfd,  in->n_type , (bfd_byte *) ext->e_type);
493     }
494   bfd_h_put_8(abfd,  in->n_sclass , ext->e_sclass);
495   bfd_h_put_8(abfd,  in->n_numaux , ext->e_numaux);
496
497   return sizeof(SYMENT);
498 }
499
500 static void
501 coff_swap_aux_in (abfd, ext1, type, class, indx, numaux, in1)
502      bfd            *abfd;
503      PTR              ext1;
504      int             type;
505      int             class;
506      int              indx;
507      int              numaux;
508      PTR              in1;
509 {
510   AUXENT    *ext = (AUXENT *)ext1;
511   union internal_auxent *in = (union internal_auxent *)in1;
512
513   switch (class) {
514   case C_FILE:
515     if (ext->x_file.x_fname[0] == 0) {
516       in->x_file.x_n.x_zeroes = 0;
517       in->x_file.x_n.x_offset = 
518         bfd_h_get_32(abfd, (bfd_byte *) ext->x_file.x_n.x_offset);
519     } else {
520 #if FILNMLEN != E_FILNMLEN
521       -> Error, we need to cope with truncating or extending FILNMLEN!;
522 #else
523       memcpy (in->x_file.x_fname, ext->x_file.x_fname, FILNMLEN);
524 #endif
525     }
526     return;
527
528
529   case C_STAT:
530 #ifdef C_LEAFSTAT
531   case C_LEAFSTAT:
532 #endif
533   case C_HIDDEN:
534     if (type == T_NULL) {
535       in->x_scn.x_scnlen = GET_SCN_SCNLEN(abfd, ext);
536       in->x_scn.x_nreloc = GET_SCN_NRELOC(abfd, ext);
537       in->x_scn.x_nlinno = GET_SCN_NLINNO(abfd, ext);
538       return;
539     }
540     break;
541   }
542
543   in->x_sym.x_tagndx.l = bfd_h_get_32(abfd, (bfd_byte *) ext->x_sym.x_tagndx);
544 #ifndef NO_TVNDX
545   in->x_sym.x_tvndx = bfd_h_get_16(abfd, (bfd_byte *) ext->x_sym.x_tvndx);
546 #endif
547
548   if (class == C_BLOCK || ISFCN (type) || ISTAG (class))
549     {
550       in->x_sym.x_fcnary.x_fcn.x_lnnoptr = GET_FCN_LNNOPTR (abfd, ext);
551       in->x_sym.x_fcnary.x_fcn.x_endndx.l = GET_FCN_ENDNDX (abfd, ext);
552     }
553   else
554     {
555 #if DIMNUM != E_DIMNUM
556  #error we need to cope with truncating or extending DIMNUM
557 #endif
558       in->x_sym.x_fcnary.x_ary.x_dimen[0] =
559         bfd_h_get_16 (abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[0]);
560       in->x_sym.x_fcnary.x_ary.x_dimen[1] =
561         bfd_h_get_16 (abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[1]);
562       in->x_sym.x_fcnary.x_ary.x_dimen[2] =
563         bfd_h_get_16 (abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[2]);
564       in->x_sym.x_fcnary.x_ary.x_dimen[3] =
565         bfd_h_get_16 (abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[3]);
566     }
567
568   if (ISFCN(type)) {
569     in->x_sym.x_misc.x_fsize = bfd_h_get_32(abfd, (bfd_byte *) ext->x_sym.x_misc.x_fsize);
570   }
571   else {
572     in->x_sym.x_misc.x_lnsz.x_lnno = GET_LNSZ_LNNO(abfd, ext);
573     in->x_sym.x_misc.x_lnsz.x_size = GET_LNSZ_SIZE(abfd, ext);
574   }
575 }
576
577 static unsigned int
578 coff_swap_aux_out (abfd, inp, type, class, indx, numaux, extp)
579      bfd   *abfd;
580      PTR        inp;
581      int   type;
582      int   class;
583      int   indx;
584      int   numaux;
585      PTR        extp;
586 {
587   union internal_auxent *in = (union internal_auxent *)inp;
588   AUXENT *ext = (AUXENT *)extp;
589
590   memset((PTR)ext, 0, AUXESZ);
591   switch (class) {
592   case C_FILE:
593     if (in->x_file.x_fname[0] == 0) {
594       bfd_h_put_32(abfd, 0, (bfd_byte *) ext->x_file.x_n.x_zeroes);
595       bfd_h_put_32(abfd,
596               in->x_file.x_n.x_offset,
597               (bfd_byte *) ext->x_file.x_n.x_offset);
598     }
599     else {
600 #if FILNMLEN != E_FILNMLEN
601       -> Error, we need to cope with truncating or extending FILNMLEN!;
602 #else
603       memcpy (ext->x_file.x_fname, in->x_file.x_fname, FILNMLEN);
604 #endif
605     }
606     return sizeof (AUXENT);
607
608
609   case C_STAT:
610 #ifdef C_LEAFSTAT
611   case C_LEAFSTAT:
612 #endif
613   case C_HIDDEN:
614     if (type == T_NULL) {
615       PUT_SCN_SCNLEN(abfd, in->x_scn.x_scnlen, ext);
616       PUT_SCN_NRELOC(abfd, in->x_scn.x_nreloc, ext);
617       PUT_SCN_NLINNO(abfd, in->x_scn.x_nlinno, ext);
618       return sizeof (AUXENT);
619     }
620     break;
621   }
622
623   bfd_h_put_32(abfd, in->x_sym.x_tagndx.l, (bfd_byte *) ext->x_sym.x_tagndx);
624 #ifndef NO_TVNDX
625   bfd_h_put_16(abfd, in->x_sym.x_tvndx , (bfd_byte *) ext->x_sym.x_tvndx);
626 #endif
627
628   if (class == C_BLOCK || ISFCN (type) || ISTAG (class))
629     {
630       PUT_FCN_LNNOPTR(abfd,  in->x_sym.x_fcnary.x_fcn.x_lnnoptr, ext);
631       PUT_FCN_ENDNDX(abfd,  in->x_sym.x_fcnary.x_fcn.x_endndx.l, ext);
632     }
633   else
634     {
635 #if DIMNUM != E_DIMNUM
636  #error we need to cope with truncating or extending DIMNUM
637 #endif
638       bfd_h_put_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[0],
639                     (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[0]);
640       bfd_h_put_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[1],
641                     (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[1]);
642       bfd_h_put_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[2],
643                     (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[2]);
644       bfd_h_put_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[3],
645                     (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[3]);
646     }
647
648   if (ISFCN (type))
649     bfd_h_put_32 (abfd, in->x_sym.x_misc.x_fsize,
650              (bfd_byte *)  ext->x_sym.x_misc.x_fsize);
651   else
652     {
653       PUT_LNSZ_LNNO (abfd, in->x_sym.x_misc.x_lnsz.x_lnno, ext);
654       PUT_LNSZ_SIZE (abfd, in->x_sym.x_misc.x_lnsz.x_size, ext);
655     }
656
657   return sizeof(AUXENT);
658 }
659
660
661 static void
662 coff_swap_lineno_in (abfd, ext1, in1)
663      bfd            *abfd;
664      PTR ext1;
665      PTR in1;
666 {
667   LINENO *ext = (LINENO *)ext1;
668   struct internal_lineno      *in = (struct internal_lineno *)in1;
669
670   in->l_addr.l_symndx = bfd_h_get_32(abfd, (bfd_byte *) ext->l_addr.l_symndx);
671   in->l_lnno = GET_LINENO_LNNO(abfd, ext);
672 }
673
674 static unsigned int
675 coff_swap_lineno_out (abfd, inp, outp)
676      bfd       *abfd;
677      PTR        inp;
678      PTR        outp;
679 {
680   struct internal_lineno *in = (struct internal_lineno *)inp;
681   struct external_lineno *ext = (struct external_lineno *)outp;
682   bfd_h_put_32(abfd, in->l_addr.l_symndx, (bfd_byte *)
683           ext->l_addr.l_symndx);
684
685   PUT_LINENO_LNNO (abfd, in->l_lnno, ext);
686   return sizeof(struct external_lineno);
687 }
688
689
690
691 static void
692 coff_swap_aouthdr_in (abfd, aouthdr_ext1, aouthdr_int1)
693      bfd            *abfd;
694      PTR aouthdr_ext1;
695      PTR aouthdr_int1;
696 {
697   struct internal_extra_pe_aouthdr *a;
698   PEAOUTHDR *src = (PEAOUTHDR *)(aouthdr_ext1);
699   AOUTHDR        *aouthdr_ext = (AOUTHDR *) aouthdr_ext1;
700   struct internal_aouthdr *aouthdr_int = (struct internal_aouthdr *)aouthdr_int1;
701
702   aouthdr_int->magic = bfd_h_get_16(abfd, (bfd_byte *) aouthdr_ext->magic);
703   aouthdr_int->vstamp = bfd_h_get_16(abfd, (bfd_byte *) aouthdr_ext->vstamp);
704   aouthdr_int->tsize =
705     GET_AOUTHDR_TSIZE (abfd, (bfd_byte *) aouthdr_ext->tsize);
706   aouthdr_int->dsize =
707     GET_AOUTHDR_DSIZE (abfd, (bfd_byte *) aouthdr_ext->dsize);
708   aouthdr_int->bsize =
709     GET_AOUTHDR_BSIZE (abfd, (bfd_byte *) aouthdr_ext->bsize);
710   aouthdr_int->entry =
711     GET_AOUTHDR_ENTRY (abfd, (bfd_byte *) aouthdr_ext->entry);
712   aouthdr_int->text_start =
713     GET_AOUTHDR_TEXT_START (abfd, (bfd_byte *) aouthdr_ext->text_start);
714   aouthdr_int->data_start =
715     GET_AOUTHDR_DATA_START (abfd, (bfd_byte *) aouthdr_ext->data_start);
716
717   a = &aouthdr_int->pe;
718   a->ImageBase = bfd_h_get_32 (abfd, src->ImageBase);
719   a->SectionAlignment = bfd_h_get_32 (abfd, src->SectionAlignment);
720   a->FileAlignment = bfd_h_get_32 (abfd, src->FileAlignment);
721   a->MajorOperatingSystemVersion = 
722     bfd_h_get_16 (abfd, src->MajorOperatingSystemVersion);
723   a->MinorOperatingSystemVersion = 
724     bfd_h_get_16 (abfd, src->MinorOperatingSystemVersion);
725   a->MajorImageVersion = bfd_h_get_16 (abfd, src->MajorImageVersion);
726   a->MinorImageVersion = bfd_h_get_16 (abfd, src->MinorImageVersion);
727   a->MajorSubsystemVersion = bfd_h_get_16 (abfd, src->MajorSubsystemVersion);
728   a->MinorSubsystemVersion = bfd_h_get_16 (abfd, src->MinorSubsystemVersion);
729   a->Reserved1 = bfd_h_get_32 (abfd, src->Reserved1);
730   a->SizeOfImage = bfd_h_get_32 (abfd, src->SizeOfImage);
731   a->SizeOfHeaders = bfd_h_get_32 (abfd, src->SizeOfHeaders);
732   a->CheckSum = bfd_h_get_32 (abfd, src->CheckSum);
733   a->Subsystem = bfd_h_get_16 (abfd, src->Subsystem);
734   a->DllCharacteristics = bfd_h_get_16 (abfd, src->DllCharacteristics);
735   a->SizeOfStackReserve = bfd_h_get_32 (abfd, src->SizeOfStackReserve);
736   a->SizeOfStackCommit = bfd_h_get_32 (abfd, src->SizeOfStackCommit);
737   a->SizeOfHeapReserve = bfd_h_get_32 (abfd, src->SizeOfHeapReserve);
738   a->SizeOfHeapCommit = bfd_h_get_32 (abfd, src->SizeOfHeapCommit);
739   a->LoaderFlags = bfd_h_get_32 (abfd, src->LoaderFlags);
740   a->NumberOfRvaAndSizes = bfd_h_get_32 (abfd, src->NumberOfRvaAndSizes);
741
742   {
743     int idx;
744     for (idx=0; idx < 16; idx++)
745       {
746         a->DataDirectory[idx].VirtualAddress =
747           bfd_h_get_32 (abfd, src->DataDirectory[idx][0]);
748         a->DataDirectory[idx].Size =
749           bfd_h_get_32 (abfd, src->DataDirectory[idx][1]);
750       }
751   }
752
753   if (aouthdr_int->entry)
754     aouthdr_int->entry += a->ImageBase;
755   if (aouthdr_int->tsize) 
756     aouthdr_int->text_start += a->ImageBase;
757   if (aouthdr_int->dsize) 
758     aouthdr_int->data_start += a->ImageBase;
759 }
760
761
762 static void add_data_entry (abfd, aout, idx, name, base)
763      bfd *abfd;
764      struct internal_extra_pe_aouthdr *aout;
765      int idx;
766      char *name;
767      bfd_vma base;
768 {
769   asection *sec = bfd_get_section_by_name (abfd, name);
770
771   /* add import directory information if it exists */
772   if (sec != NULL)
773     {
774       aout->DataDirectory[idx].VirtualAddress = sec->lma - base;
775       aout->DataDirectory[idx].Size = sec->_cooked_size;
776       sec->flags |= SEC_DATA;
777     }
778 }
779
780 static unsigned int
781 coff_swap_aouthdr_out (abfd, in, out)
782      bfd       *abfd;
783      PTR        in;
784      PTR        out;
785 {
786   struct internal_aouthdr *aouthdr_in = (struct internal_aouthdr *)in;
787   struct internal_extra_pe_aouthdr *extra = &pe_data (abfd)->pe_opthdr;
788   PEAOUTHDR *aouthdr_out = (PEAOUTHDR *)out;
789
790   bfd_vma sa = extra->SectionAlignment;
791   bfd_vma fa = extra->FileAlignment;
792   bfd_vma ib = extra->ImageBase ;
793
794   if (aouthdr_in->tsize) 
795     aouthdr_in->text_start -= ib;
796   if (aouthdr_in->dsize) 
797     aouthdr_in->data_start -= ib;
798   if (aouthdr_in->entry) 
799     aouthdr_in->entry -= ib;
800
801 #define FA(x)  (((x) + fa -1 ) & (- fa))
802 #define SA(x)  (((x) + sa -1 ) & (- sa))
803
804   /* We like to have the sizes aligned */
805
806   aouthdr_in->bsize = FA (aouthdr_in->bsize);
807
808
809   extra->NumberOfRvaAndSizes = IMAGE_NUMBEROF_DIRECTORY_ENTRIES;
810
811   /* first null out all data directory entries .. */
812   memset (extra->DataDirectory, sizeof (extra->DataDirectory), 0);
813
814   add_data_entry (abfd, extra, 0, ".edata", ib);
815   add_data_entry (abfd, extra, 1, ".idata", ib);
816   add_data_entry (abfd, extra, 2, ".rsrc" ,ib);
817
818 #ifdef POWERPC_LE_PE
819   /* FIXME: do other PE platforms use this? */
820   add_data_entry (abfd, extra, 3, ".pdata" ,ib);
821 #endif
822
823   add_data_entry (abfd, extra, 5, ".reloc", ib);
824
825 #ifdef POWERPC_LE_PE
826   /* On the PPC NT system, this field is set up as follows. It is
827      not an "officially" reserved field, so it currently has no title.
828      first_thunk_address is idata$5, and the thunk_size is the size
829      of the idata$5 chunk of the idata section.
830   */
831   extra->DataDirectory[12].VirtualAddress = first_thunk_address;
832   extra->DataDirectory[12].Size = thunk_size;
833
834   /* On the PPC NT system, the size of the directory entry is not the
835      size of the entire section. It's actually offset to the end of 
836      the idata$3 component of the idata section. This is the size of
837      the entire import table. (also known as the start of idata$4)
838   */
839   extra->DataDirectory[1].Size = import_table_size;
840 #endif
841
842   {
843     asection *sec;
844     bfd_vma dsize= 0;
845     bfd_vma isize = SA(abfd->sections->filepos);
846     bfd_vma tsize= 0;
847 #ifdef PPC
848     isize = 0;
849 #endif
850     for (sec = abfd->sections; sec; sec = sec->next)
851       {
852         int rounded = FA(sec->_raw_size);
853         if (sec->flags & SEC_DATA) 
854           dsize += rounded;
855         if (sec->flags & SEC_CODE)
856           tsize += rounded;
857         isize += SA(rounded);
858       }
859
860     aouthdr_in->dsize = dsize;
861     aouthdr_in->tsize = tsize;
862     extra->SizeOfImage = isize;
863   }
864
865   extra->SizeOfHeaders = abfd->sections->filepos;
866   bfd_h_put_16(abfd, aouthdr_in->magic, (bfd_byte *) aouthdr_out->standard.magic);
867
868 #ifdef POWERPC_LE_PE
869   /* this little piece of magic sets the "linker version" field to 2.60 */
870   bfd_h_put_16(abfd, 2  + 60 * 256, (bfd_byte *) aouthdr_out->standard.vstamp);
871 #else
872   /* this little piece of magic sets the "linker version" field to 2.55 */
873   bfd_h_put_16(abfd, 2  + 55 * 256, (bfd_byte *) aouthdr_out->standard.vstamp);
874 #endif
875
876   PUT_AOUTHDR_TSIZE (abfd, aouthdr_in->tsize, (bfd_byte *) aouthdr_out->standard.tsize);
877   PUT_AOUTHDR_DSIZE (abfd, aouthdr_in->dsize, (bfd_byte *) aouthdr_out->standard.dsize);
878   PUT_AOUTHDR_BSIZE (abfd, aouthdr_in->bsize, (bfd_byte *) aouthdr_out->standard.bsize);
879   PUT_AOUTHDR_ENTRY (abfd, aouthdr_in->entry, (bfd_byte *) aouthdr_out->standard.entry);
880   PUT_AOUTHDR_TEXT_START (abfd, aouthdr_in->text_start,
881                           (bfd_byte *) aouthdr_out->standard.text_start);
882
883   PUT_AOUTHDR_DATA_START (abfd, aouthdr_in->data_start,
884                           (bfd_byte *) aouthdr_out->standard.data_start);
885
886
887   bfd_h_put_32 (abfd, extra->ImageBase, 
888                 (bfd_byte *) aouthdr_out->ImageBase);
889   bfd_h_put_32 (abfd, extra->SectionAlignment,
890                 (bfd_byte *) aouthdr_out->SectionAlignment);
891   bfd_h_put_32 (abfd, extra->FileAlignment,
892                 (bfd_byte *) aouthdr_out->FileAlignment);
893   bfd_h_put_16 (abfd, extra->MajorOperatingSystemVersion,
894                 (bfd_byte *) aouthdr_out->MajorOperatingSystemVersion);
895   bfd_h_put_16 (abfd, extra->MinorOperatingSystemVersion,
896                 (bfd_byte *) aouthdr_out->MinorOperatingSystemVersion);
897   bfd_h_put_16 (abfd, extra->MajorImageVersion,
898                 (bfd_byte *) aouthdr_out->MajorImageVersion);
899   bfd_h_put_16 (abfd, extra->MinorImageVersion,
900                 (bfd_byte *) aouthdr_out->MinorImageVersion);
901   bfd_h_put_16 (abfd, extra->MajorSubsystemVersion,
902                 (bfd_byte *) aouthdr_out->MajorSubsystemVersion);
903   bfd_h_put_16 (abfd, extra->MinorSubsystemVersion,
904                 (bfd_byte *) aouthdr_out->MinorSubsystemVersion);
905   bfd_h_put_32 (abfd, extra->Reserved1,
906                 (bfd_byte *) aouthdr_out->Reserved1);
907   bfd_h_put_32 (abfd, extra->SizeOfImage,
908                 (bfd_byte *) aouthdr_out->SizeOfImage);
909   bfd_h_put_32 (abfd, extra->SizeOfHeaders,
910                 (bfd_byte *) aouthdr_out->SizeOfHeaders);
911   bfd_h_put_32 (abfd, extra->CheckSum,
912                 (bfd_byte *) aouthdr_out->CheckSum);
913   bfd_h_put_16 (abfd, extra->Subsystem,
914                 (bfd_byte *) aouthdr_out->Subsystem);
915   bfd_h_put_16 (abfd, extra->DllCharacteristics,
916                 (bfd_byte *) aouthdr_out->DllCharacteristics);
917   bfd_h_put_32 (abfd, extra->SizeOfStackReserve,
918                 (bfd_byte *) aouthdr_out->SizeOfStackReserve);
919   bfd_h_put_32 (abfd, extra->SizeOfStackCommit,
920                 (bfd_byte *) aouthdr_out->SizeOfStackCommit);
921   bfd_h_put_32 (abfd, extra->SizeOfHeapReserve,
922                 (bfd_byte *) aouthdr_out->SizeOfHeapReserve);
923   bfd_h_put_32 (abfd, extra->SizeOfHeapCommit,
924                 (bfd_byte *) aouthdr_out->SizeOfHeapCommit);
925   bfd_h_put_32 (abfd, extra->LoaderFlags,
926                 (bfd_byte *) aouthdr_out->LoaderFlags);
927   bfd_h_put_32 (abfd, extra->NumberOfRvaAndSizes,
928                 (bfd_byte *) aouthdr_out->NumberOfRvaAndSizes);
929   {
930     int idx;
931     for (idx=0; idx < 16; idx++)
932       {
933         bfd_h_put_32 (abfd, extra->DataDirectory[idx].VirtualAddress,
934                       (bfd_byte *) aouthdr_out->DataDirectory[idx][0]);
935         bfd_h_put_32 (abfd, extra->DataDirectory[idx].Size,
936                       (bfd_byte *) aouthdr_out->DataDirectory[idx][1]);
937       }
938   }
939
940   return sizeof(AOUTHDR);
941 }
942
943 static void
944     coff_swap_scnhdr_in (abfd, ext, in)
945       bfd            *abfd;
946   PTR        ext;
947   PTR        in;
948 {
949   SCNHDR *scnhdr_ext = (SCNHDR *) ext;
950   struct internal_scnhdr *scnhdr_int = (struct internal_scnhdr *) in;
951
952   memcpy(scnhdr_int->s_name, scnhdr_ext->s_name, sizeof(scnhdr_int->s_name));
953   scnhdr_int->s_vaddr =
954     GET_SCNHDR_VADDR (abfd, (bfd_byte *) scnhdr_ext->s_vaddr);
955   scnhdr_int->s_paddr =
956     GET_SCNHDR_PADDR (abfd, (bfd_byte *) scnhdr_ext->s_paddr);
957   scnhdr_int->s_size =
958     GET_SCNHDR_SIZE (abfd, (bfd_byte *) scnhdr_ext->s_size);
959   scnhdr_int->s_scnptr =
960     GET_SCNHDR_SCNPTR (abfd, (bfd_byte *) scnhdr_ext->s_scnptr);
961   scnhdr_int->s_relptr =
962     GET_SCNHDR_RELPTR (abfd, (bfd_byte *) scnhdr_ext->s_relptr);
963   scnhdr_int->s_lnnoptr =
964     GET_SCNHDR_LNNOPTR (abfd, (bfd_byte *) scnhdr_ext->s_lnnoptr);
965   scnhdr_int->s_flags = bfd_h_get_32(abfd, (bfd_byte *) scnhdr_ext->s_flags);
966
967   scnhdr_int->s_nreloc = bfd_h_get_16(abfd, (bfd_byte *) scnhdr_ext->s_nreloc);
968   scnhdr_int->s_nlnno = bfd_h_get_16(abfd, (bfd_byte *) scnhdr_ext->s_nlnno);
969
970   if (scnhdr_int->s_vaddr != 0) 
971     {
972       scnhdr_int->s_vaddr += pe_data (abfd)->pe_opthdr.ImageBase;
973     }
974   if (strcmp (scnhdr_int->s_name, _BSS) == 0) 
975     {
976       scnhdr_int->s_size = scnhdr_int->s_paddr;
977       scnhdr_int->s_paddr = 0;
978     }
979 }
980
981 static unsigned int
982 coff_swap_scnhdr_out (abfd, in, out)
983      bfd       *abfd;
984      PTR        in;
985      PTR        out;
986 {
987   struct internal_scnhdr *scnhdr_int = (struct internal_scnhdr *)in;
988   SCNHDR *scnhdr_ext = (SCNHDR *)out;
989   unsigned int ret = sizeof (SCNHDR);
990   bfd_vma ps;
991   bfd_vma ss;
992
993   memcpy(scnhdr_ext->s_name, scnhdr_int->s_name, sizeof(scnhdr_int->s_name));
994
995   PUT_SCNHDR_VADDR (abfd, 
996                     (scnhdr_int->s_vaddr 
997                      - pe_data(abfd)->pe_opthdr.ImageBase),
998                     (bfd_byte *) scnhdr_ext->s_vaddr);
999
1000   /* NT wants the size data to be rounded up to the next NT_FILE_ALIGNMENT
1001      value except for the BSS section, its s_size should be 0 */
1002
1003
1004   if (strcmp (scnhdr_int->s_name, _BSS) == 0) 
1005     {
1006       ps = scnhdr_int->s_size;
1007       ss = 0;
1008     }
1009   else
1010     {
1011       ps = scnhdr_int->s_paddr;
1012       ss = scnhdr_int->s_size;
1013     }
1014
1015   PUT_SCNHDR_SIZE (abfd, ss,
1016                    (bfd_byte *) scnhdr_ext->s_size);
1017
1018
1019   PUT_SCNHDR_PADDR (abfd, ps, (bfd_byte *) scnhdr_ext->s_paddr);
1020
1021   PUT_SCNHDR_SCNPTR (abfd, scnhdr_int->s_scnptr,
1022                      (bfd_byte *) scnhdr_ext->s_scnptr);
1023   PUT_SCNHDR_RELPTR (abfd, scnhdr_int->s_relptr,
1024                      (bfd_byte *) scnhdr_ext->s_relptr);
1025   PUT_SCNHDR_LNNOPTR (abfd, scnhdr_int->s_lnnoptr,
1026                       (bfd_byte *) scnhdr_ext->s_lnnoptr);
1027
1028   /* Extra flags must be set when dealing with NT.  All sections should also
1029      have the IMAGE_SCN_MEM_READ (0x40000000) flag set.  In addition, the
1030      .text section must have IMAGE_SCN_MEM_EXECUTE (0x20000000) and the data
1031      sections (.idata, .data, .bss, .CRT) must have IMAGE_SCN_MEM_WRITE set
1032      (this is especially important when dealing with the .idata section since
1033      the addresses for routines from .dlls must be overwritten).  If .reloc
1034      section data is ever generated, we must add IMAGE_SCN_MEM_DISCARDABLE
1035      (0x02000000).  Also, the resource data should also be read and
1036      writable.  */
1037
1038   /* FIXME: alignment is also encoded in this field, at least on ppc (krk) */
1039   /* FIXME: even worse, I don't see how to get the original alignment field*/
1040   /*        back...                                                        */
1041
1042   {
1043     int flags = scnhdr_int->s_flags;
1044     if (strcmp (scnhdr_int->s_name, ".data")  == 0 ||
1045         strcmp (scnhdr_int->s_name, ".CRT")   == 0 ||
1046         strcmp (scnhdr_int->s_name, ".rsrc")  == 0 ||
1047         strcmp (scnhdr_int->s_name, ".bss")   == 0)
1048       flags |= IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_WRITE;
1049     else if (strcmp (scnhdr_int->s_name, ".text") == 0)
1050       flags |= IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_EXECUTE;
1051     else if (strcmp (scnhdr_int->s_name, ".reloc") == 0)
1052       flags = SEC_DATA| IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_DISCARDABLE;
1053     else if (strcmp (scnhdr_int->s_name, ".idata") == 0)
1054       flags = IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_WRITE | SEC_DATA;     
1055     else if (strcmp (scnhdr_int->s_name, ".rdata") == 0
1056              || strcmp (scnhdr_int->s_name, ".edata") == 0)
1057       flags =  IMAGE_SCN_MEM_READ | SEC_DATA;     
1058     /* ppc-nt additions */
1059     else if (strcmp (scnhdr_int->s_name, ".pdata") == 0)
1060       flags = IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_ALIGN_4BYTES |
1061                           IMAGE_SCN_MEM_READ ;
1062     /* Remember this field is a max of 8 chars, so the null is _not_ there
1063        for an 8 character name like ".reldata". (yep. Stupid bug) */
1064     else if (strncmp (scnhdr_int->s_name, ".reldata", strlen(".reldata")) == 0)
1065       flags =  IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_ALIGN_8BYTES |
1066                IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_WRITE ;
1067     else if (strcmp (scnhdr_int->s_name, ".ydata") == 0)
1068       flags =  IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_ALIGN_8BYTES |
1069                IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_WRITE ;
1070     else if (strcmp (scnhdr_int->s_name, ".drectve") == 0)
1071       flags =  IMAGE_SCN_LNK_INFO | IMAGE_SCN_LNK_REMOVE ;
1072     /* end of ppc-nt additions */
1073
1074     bfd_h_put_32(abfd, flags, (bfd_byte *) scnhdr_ext->s_flags);
1075   }
1076
1077   if (scnhdr_int->s_nlnno <= 0xffff)
1078     bfd_h_put_16(abfd, scnhdr_int->s_nlnno, (bfd_byte *) scnhdr_ext->s_nlnno);
1079   else
1080     {
1081       (*_bfd_error_handler) ("%s: line number overflow: 0x%lx > 0xffff",
1082                              bfd_get_filename (abfd),
1083                              scnhdr_int->s_nlnno);
1084       bfd_set_error (bfd_error_file_truncated);
1085       bfd_h_put_16 (abfd, 0xffff, (bfd_byte *) scnhdr_ext->s_nlnno);
1086       ret = 0;
1087     }
1088   if (scnhdr_int->s_nreloc <= 0xffff)
1089     bfd_h_put_16(abfd, scnhdr_int->s_nreloc, (bfd_byte *) scnhdr_ext->s_nreloc);
1090   else
1091     {
1092       (*_bfd_error_handler) ("%s: reloc overflow: 0x%lx > 0xffff",
1093                              bfd_get_filename (abfd),
1094                              scnhdr_int->s_nreloc);
1095       bfd_set_error (bfd_error_file_truncated);
1096       bfd_h_put_16 (abfd, 0xffff, (bfd_byte *) scnhdr_ext->s_nreloc);
1097       ret = 0;
1098     }
1099   return ret;
1100 }
1101
1102 static char * dir_names[IMAGE_NUMBEROF_DIRECTORY_ENTRIES] = 
1103 {
1104   "Export Directory [.edata]",
1105   "Import Directory [parts of .idata]",
1106   "Resource Directory [.rsrc]",
1107   "Exception Directory [.pdata]",
1108   "Security Directory",
1109   "Base Relocation Directory [.reloc]",
1110   "Debug Directory",
1111   "Description Directory",
1112   "Special Directory",
1113   "Thread Storage Directory [.tls]",
1114   "Load Configuration Directory",
1115   "Bound Import Directory",
1116   "Import Address Table Directory",
1117   "Reserved",
1118   "Reserved",
1119   "Reserved"
1120 };
1121
1122 /**********************************************************************/
1123 static boolean
1124 pe_print_idata(abfd, vfile)
1125      bfd*abfd;
1126      void *vfile;
1127 {
1128   FILE *file = vfile;
1129   bfd_byte *data = 0;
1130   asection *section = bfd_get_section_by_name (abfd, ".idata");
1131
1132 #ifdef POWERPC_LE_PE
1133   asection *rel_section = bfd_get_section_by_name (abfd, ".reldata");
1134 #endif
1135
1136   bfd_size_type datasize = 0;
1137   bfd_size_type i;
1138   bfd_size_type start, stop;
1139   int onaline = 20;
1140   bfd_vma addr_value;
1141   bfd_vma loadable_toc_address;
1142   bfd_vma toc_address;
1143   bfd_vma start_address;
1144
1145   pe_data_type *pe = pe_data (abfd);
1146   struct internal_extra_pe_aouthdr *extra = &pe->pe_opthdr;
1147
1148   if (section == 0)
1149     return true;
1150
1151 #ifdef POWERPC_LE_PE
1152   if (rel_section != 0 && bfd_section_size (abfd, rel_section) != 0)
1153     {
1154       /* The toc address can be found by taking the starting address,
1155          which on the PPC locates a function descriptor. The descriptor
1156          consists of the function code starting address followed by the
1157          address of the toc. The starting address we get from the bfd,
1158          and the descriptor is supposed to be in the .reldata section. 
1159       */
1160
1161       bfd_byte *data = 0;
1162       int offset;
1163       data = (bfd_byte *) bfd_malloc ((size_t) bfd_section_size (abfd, 
1164                                                                  rel_section));
1165       if (data == NULL && bfd_section_size (abfd, rel_section) != 0)
1166         return false;
1167       datasize = bfd_section_size (abfd, rel_section);
1168   
1169       bfd_get_section_contents (abfd, 
1170                                 rel_section, 
1171                                 (PTR) data, 0, 
1172                                 bfd_section_size (abfd, rel_section));
1173
1174       offset = abfd->start_address - rel_section->vma;
1175
1176       start_address = bfd_get_32(abfd, data+offset);
1177       loadable_toc_address = bfd_get_32(abfd, data+offset+4);
1178       toc_address = loadable_toc_address - 32768;
1179       fprintf(file,
1180               "\nFunction descriptor located at the start address:\n");
1181       fprintf (file,
1182                " %04lx code-base %08lx toc (loadable) %08lx toc (actual) %08lx\n", 
1183                (unsigned long int) (abfd->start_address),
1184                start_address, loadable_toc_address, toc_address);
1185     }
1186   else
1187     {
1188       loadable_toc_address = 0; 
1189       toc_address = 0; 
1190       start_address = 0;
1191     }
1192 #endif
1193
1194   fprintf(file,
1195           "\nThe Import Tables (interpreted .idata section contents)\n");
1196   fprintf(file,
1197           " vma:    Hint    Time      Forward  DLL       First\n");
1198   fprintf(file,
1199           "         Table   Stamp     Chain    Name      Thunk\n");
1200
1201   if (bfd_section_size (abfd, section) == 0)
1202     return true;
1203
1204   data = (bfd_byte *) bfd_malloc ((size_t) bfd_section_size (abfd, section));
1205   datasize = bfd_section_size (abfd, section);
1206   if (data == NULL && datasize != 0)
1207     return false;
1208
1209   bfd_get_section_contents (abfd, 
1210                             section, 
1211                             (PTR) data, 0, 
1212                             bfd_section_size (abfd, section));
1213
1214   start = 0;
1215
1216   stop = bfd_section_size (abfd, section);
1217
1218   for (i = start; i < stop; i += onaline)
1219     {
1220       bfd_vma hint_addr;
1221       bfd_vma time_stamp;
1222       bfd_vma forward_chain;
1223       bfd_vma dll_name;
1224       bfd_vma first_thunk;
1225       int idx;
1226       int j;
1227       char *dll;
1228       int adj = extra->ImageBase - section->vma;
1229
1230       fprintf (file,
1231                " %04lx\t", 
1232                (unsigned long int) (i + section->vma));
1233       
1234       if (i+20 > stop)
1235         {
1236           /* check stuff */
1237           ;
1238         }
1239       
1240       hint_addr = bfd_get_32(abfd, data+i);
1241       time_stamp = bfd_get_32(abfd, data+i+4);
1242       forward_chain = bfd_get_32(abfd, data+i+8);
1243       dll_name = bfd_get_32(abfd, data+i+12);
1244       first_thunk = bfd_get_32(abfd, data+i+16);
1245       
1246       fprintf(file, "%08lx %08lx %08lx %08lx %08lx\n",
1247               hint_addr,
1248               time_stamp,
1249               forward_chain,
1250               dll_name,
1251               first_thunk);
1252
1253       if (hint_addr ==0)
1254         {
1255           break;
1256         }
1257
1258       /* the image base is present in the section->vma */
1259       dll = data + dll_name + adj;
1260       fprintf(file, "\n\tDLL Name: %s\n", dll);
1261       fprintf(file, "\tvma:  Ordinal  Member-Name\n");
1262
1263       idx = hint_addr + adj;
1264
1265       for (j=0;j<stop;j+=4)
1266         {
1267           int ordinal;
1268           char *member_name;
1269           bfd_vma member = bfd_get_32(abfd, data + idx + j);
1270           if (member == 0)
1271             break;
1272           ordinal = bfd_get_16(abfd,
1273                                data + member + adj);
1274           member_name = data + member + adj + 2;
1275           fprintf(file, "\t%04lx\t %4d  %s\n",
1276                   member, ordinal, member_name);
1277         }
1278
1279       if (hint_addr != first_thunk) 
1280         {
1281           int differ = 0;
1282           int idx2;
1283
1284           idx2 = first_thunk + adj;
1285
1286           for (j=0;j<stop;j+=4)
1287             {
1288               int ordinal;
1289               char *member_name;
1290               bfd_vma hint_member = bfd_get_32(abfd, data + idx + j);
1291               bfd_vma iat_member = bfd_get_32(abfd, data + idx2 + j);
1292               if (hint_member != iat_member)
1293                 {
1294                   if (differ == 0)
1295                     {
1296                       fprintf(file, 
1297                               "\tThe Import Address Table (difference found)\n");
1298                       fprintf(file, "\tvma:  Ordinal  Member-Name\n");
1299                       differ = 1;
1300                     }
1301                   if (iat_member == 0)
1302                     {
1303                       fprintf(file,
1304                               "\t>>> Ran out of IAT members!\n");
1305                     }
1306                   else 
1307                     {
1308                       ordinal = bfd_get_16(abfd,
1309                                            data + iat_member + adj);
1310                       member_name = data + iat_member + adj + 2;
1311                       fprintf(file, "\t%04lx\t %4d  %s\n",
1312                               iat_member, ordinal, member_name);
1313                     }
1314                   break;
1315                 }
1316               if (hint_member == 0)
1317                 break;
1318             }
1319           if (differ == 0)
1320             {
1321               fprintf(file,
1322                       "\tThe Import Address Table is identical\n");
1323             }
1324         }
1325
1326       fprintf(file, "\n");
1327
1328     }
1329
1330
1331   free (data);
1332 }
1333 static boolean
1334 pe_print_pdata(abfd, vfile)
1335      bfd*abfd;
1336      void *vfile;
1337 {
1338   FILE *file = vfile;
1339   bfd_byte *data = 0;
1340   asection *section = bfd_get_section_by_name (abfd, ".pdata");
1341   bfd_size_type datasize = 0;
1342   bfd_size_type i;
1343   bfd_size_type start, stop;
1344   int onaline = 20;
1345   bfd_vma addr_value;
1346
1347   if (section == 0)
1348     return true;
1349
1350   fprintf(file,
1351           "\nThe Function Table (interpreted .pdata section contents)\n");
1352   fprintf(file,
1353           " vma:   Begin    End      EH       EH       PrologEnd\n");
1354   fprintf(file,
1355           "        Address  Address  Handler  Data     Address\n");
1356
1357   if (bfd_section_size (abfd, section) == 0)
1358     return true;
1359
1360   data = (bfd_byte *) bfd_malloc ((size_t) bfd_section_size (abfd, section));
1361   datasize = bfd_section_size (abfd, section);
1362   if (data == NULL && datasize != 0)
1363     return false;
1364
1365   bfd_get_section_contents (abfd, 
1366                             section, 
1367                             (PTR) data, 0, 
1368                             bfd_section_size (abfd, section));
1369
1370   start = 0;
1371
1372   stop = bfd_section_size (abfd, section);
1373
1374   for (i = start; i < stop; i += onaline)
1375     {
1376       bfd_vma begin_addr;
1377       bfd_vma end_addr;
1378       bfd_vma eh_handler;
1379       bfd_vma eh_data;
1380       bfd_vma prolog_end_addr;
1381
1382       if (i+20 > stop)
1383           break;
1384       
1385       begin_addr = bfd_get_32(abfd, data+i);
1386       end_addr = bfd_get_32(abfd, data+i+4);
1387       eh_handler = bfd_get_32(abfd, data+i+8);
1388       eh_data = bfd_get_32(abfd, data+i+12);
1389       prolog_end_addr = bfd_get_32(abfd, data+i+16);
1390       
1391       if (begin_addr == 0)
1392         {
1393           /* We are probably into the padding of the
1394              section now */
1395           break;
1396         }
1397
1398       fprintf (file,
1399                " %04lx\t", 
1400                (unsigned long int) (i + section->vma));
1401
1402       fprintf(file, "%08lx %08lx %08lx %08lx %08lx",
1403               begin_addr,
1404               end_addr,
1405               eh_handler,
1406               eh_data,
1407               prolog_end_addr);
1408
1409 #ifdef POWERPC_LE_PE
1410       if (eh_handler == 0 && eh_data != 0)
1411         {
1412           /* Special bits here, although the meaning may */
1413           /* be a little mysterious. The only one I know */
1414           /* for sure is 0x03.                           */
1415           /* Code Significance                           */
1416           /* 0x00 None                                   */
1417           /* 0x01 Register Save Millicode                */
1418           /* 0x02 Register Restore Millicode             */
1419           /* 0x03 Glue Code Sequence                     */
1420           switch (eh_data)
1421             {
1422             case 0x01:
1423               fprintf(file, " Register save millicode");
1424               break;
1425             case 0x02:
1426               fprintf(file, " Register restore millicode");
1427               break;
1428             case 0x03:
1429               fprintf(file, " Glue code sequence");
1430               break;
1431             default:
1432               break;
1433             }
1434         }
1435 #endif     
1436       fprintf(file, "\n");
1437     }
1438
1439   free (data);
1440 }
1441
1442 static boolean
1443 pe_print_private_bfd_data (abfd, vfile)
1444      bfd *abfd;
1445      PTR vfile;
1446 {
1447   FILE *file = (FILE *) vfile;
1448   int j;
1449   pe_data_type *pe = pe_data (abfd);
1450   struct internal_extra_pe_aouthdr *i = &pe->pe_opthdr;
1451
1452   fprintf (file,"\nImageBase\t\t");
1453   fprintf_vma (file, i->ImageBase);
1454   fprintf (file,"\nSectionAlignment\t");
1455   fprintf_vma (file, i->SectionAlignment);
1456   fprintf (file,"\nFileAlignment\t\t");
1457   fprintf_vma (file, i->FileAlignment);
1458   fprintf (file,"\nMajorOSystemVersion\t%d\n", i->MajorOperatingSystemVersion);
1459   fprintf (file,"MinorOSystemVersion\t%d\n", i->MinorOperatingSystemVersion);
1460   fprintf (file,"MajorImageVersion\t%d\n", i->MajorImageVersion);
1461   fprintf (file,"MinorImageVersion\t%d\n", i->MinorImageVersion);
1462   fprintf (file,"MajorSubsystemVersion\t%d\n", i->MajorSubsystemVersion);
1463   fprintf (file,"MinorSubsystemVersion\t%d\n", i->MinorSubsystemVersion);
1464   fprintf (file,"Reserved1\t\t%08lx\n", i->Reserved1);
1465   fprintf (file,"SizeOfImage\t\t%08lx\n", i->SizeOfImage);
1466   fprintf (file,"SizeOfHeaders\t\t%08lx\n", i->SizeOfHeaders);
1467   fprintf (file,"CheckSum\t\t%08lx\n", i->CheckSum);
1468   fprintf (file,"Subsystem\t\t%08x\n", i->Subsystem);
1469   fprintf (file,"DllCharacteristics\t%08x\n", i->DllCharacteristics);
1470   fprintf (file,"SizeOfStackReserve\t");
1471   fprintf_vma (file, i->SizeOfStackReserve);
1472   fprintf (file,"\nSizeOfStackCommit\t");
1473   fprintf_vma (file, i->SizeOfStackCommit);
1474   fprintf (file,"\nSizeOfHeapReserve\t");
1475   fprintf_vma (file, i->SizeOfHeapReserve);
1476   fprintf (file,"\nSizeOfHeapCommit\t");
1477   fprintf_vma (file, i->SizeOfHeapCommit);
1478   fprintf (file,"\nLoaderFlags\t\t%08lx\n", i->LoaderFlags);
1479   fprintf (file,"NumberOfRvaAndSizes\t%08lx\n", i->NumberOfRvaAndSizes);
1480
1481   fprintf (file,"\nThe Data Directory\n");
1482   for (j = 0; j < IMAGE_NUMBEROF_DIRECTORY_ENTRIES; j++) 
1483     {
1484       fprintf (file, "Entry %1x ", j);
1485       fprintf_vma (file, i->DataDirectory[j].VirtualAddress);
1486       fprintf (file, " %08lx ", i->DataDirectory[j].Size);
1487       fprintf (file, "%s\n", dir_names[j]);
1488     }
1489
1490   pe_print_idata(abfd, vfile);
1491   pe_print_pdata(abfd, vfile);
1492
1493   return true;
1494 }
1495
1496 static boolean
1497 pe_mkobject (abfd)
1498      bfd * abfd;
1499 {
1500   pe_data_type *pe;
1501   abfd->tdata.pe_obj_data = 
1502     (struct pe_tdata *) bfd_zalloc (abfd, sizeof (pe_data_type));
1503
1504   if (abfd->tdata.pe_obj_data == 0)
1505     return false;
1506
1507   pe = pe_data (abfd);
1508
1509   pe->coff.pe = 1;
1510   pe->in_reloc_p = in_reloc_p;
1511   return true;
1512 }
1513
1514 /* Create the COFF backend specific information.  */
1515 static PTR
1516 pe_mkobject_hook (abfd, filehdr, aouthdr)
1517      bfd * abfd;
1518      PTR filehdr;
1519      PTR aouthdr;
1520 {
1521   struct internal_filehdr *internal_f = (struct internal_filehdr *) filehdr;
1522   pe_data_type *pe;
1523
1524   if (pe_mkobject (abfd) == false)
1525     return NULL;
1526
1527   pe = pe_data (abfd);
1528   pe->coff.sym_filepos = internal_f->f_symptr;
1529   /* These members communicate important constants about the symbol
1530      table to GDB's symbol-reading code.  These `constants'
1531      unfortunately vary among coff implementations...  */
1532   pe->coff.local_n_btmask = N_BTMASK;
1533   pe->coff.local_n_btshft = N_BTSHFT;
1534   pe->coff.local_n_tmask = N_TMASK;
1535   pe->coff.local_n_tshift = N_TSHIFT;
1536   pe->coff.local_symesz = SYMESZ;
1537   pe->coff.local_auxesz = AUXESZ;
1538   pe->coff.local_linesz = LINESZ;
1539
1540   obj_raw_syment_count (abfd) =
1541     obj_conv_table_size (abfd) =
1542       internal_f->f_nsyms;
1543
1544   pe->real_flags = internal_f->f_flags;
1545
1546 #ifdef COFF_IMAGE_WITH_PE
1547   if (aouthdr) 
1548     {
1549       pe->pe_opthdr = ((struct internal_aouthdr *)aouthdr)->pe;
1550     }
1551 #endif
1552
1553   return (PTR) pe;
1554 }
1555
1556
1557
1558 /* Copy any private info we understand from the input bfd
1559    to the output bfd.  */
1560
1561 #define coff_bfd_copy_private_bfd_data pe_bfd_copy_private_bfd_data
1562
1563 static boolean
1564 pe_bfd_copy_private_bfd_data (ibfd, obfd)
1565      bfd *ibfd, *obfd;
1566 {
1567   /* One day we may try to grok other private data.  */
1568   if (ibfd->xvec->flavour != bfd_target_coff_flavour
1569       || obfd->xvec->flavour != bfd_target_coff_flavour)
1570     return true;
1571
1572   pe_data(obfd)->pe_opthdr = pe_data (ibfd)->pe_opthdr;
1573
1574   return true;
1575 }