* peicode.h (coff_swap_sym_in): When we create the actual section
[platform/upstream/binutils.git] / bfd / peicode.h
1 /* Support for the generic parts of most COFF variants, for BFD.
2    Copyright 1995, 1996, 1997, 1998 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 /* Hey look, some documentation [and in a place you expect to find it]!
27
28    The main reference for the pei format is "Microsoft Portable Executable
29    and Common Object File Format Specification 4.1".  Get it if you need to
30    do some serious hacking on this code.
31
32    Another reference:
33    "Peering Inside the PE: A Tour of the Win32 Portable Executable
34    File Format", MSJ 1994, Volume 9.
35
36    The *sole* difference between the pe format and the pei format is that the
37    latter has an MSDOS 2.0 .exe header on the front that prints the message
38    "This app must be run under Windows." (or some such).
39    (FIXME: Whether that statement is *really* true or not is unknown.
40    Are there more subtle differences between pe and pei formats?
41    For now assume there aren't.  If you find one, then for God sakes
42    document it here!)
43
44    The Microsoft docs use the word "image" instead of "executable" because
45    the former can also refer to a DLL (shared library).  Confusion can arise
46    because the `i' in `pei' also refers to "image".  The `pe' format can
47    also create images (i.e. executables), it's just that to run on a win32
48    system you need to use the pei format.
49
50    FIXME: Please add more docs here so the next poor fool that has to hack
51    on this code has a chance of getting something accomplished without
52    wasting too much time.
53 */
54
55 #ifdef coff_bfd_print_private_bfd_data
56 static boolean (*pe_saved_coff_bfd_print_private_bfd_data)
57      PARAMS ((bfd *, PTR))
58      = coff_bfd_print_private_bfd_data;
59 #undef coff_bfd_print_private_bfd_data
60 #else
61 static boolean (*pe_saved_coff_bfd_print_private_bfd_data)
62      PARAMS ((bfd *, PTR))
63      = NULL;
64 #endif
65 #define coff_bfd_print_private_bfd_data pe_print_private_bfd_data
66
67 #define coff_mkobject      pe_mkobject
68 #define coff_mkobject_hook pe_mkobject_hook
69
70 #ifndef GET_FCN_LNNOPTR
71 #define GET_FCN_LNNOPTR(abfd, ext) \
72      bfd_h_get_32(abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_fcn.x_lnnoptr)
73 #endif
74
75 #ifndef GET_FCN_ENDNDX
76 #define GET_FCN_ENDNDX(abfd, ext)  \
77         bfd_h_get_32(abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_fcn.x_endndx)
78 #endif
79
80 #ifndef PUT_FCN_LNNOPTR
81 #define PUT_FCN_LNNOPTR(abfd, in, ext)  bfd_h_put_32(abfd,  in, (bfd_byte *) ext->x_sym.x_fcnary.x_fcn.x_lnnoptr)
82 #endif
83 #ifndef PUT_FCN_ENDNDX
84 #define PUT_FCN_ENDNDX(abfd, in, ext) bfd_h_put_32(abfd, in, (bfd_byte *) ext->x_sym.x_fcnary.x_fcn.x_endndx)
85 #endif
86 #ifndef GET_LNSZ_LNNO
87 #define GET_LNSZ_LNNO(abfd, ext) bfd_h_get_16(abfd, (bfd_byte *) ext->x_sym.x_misc.x_lnsz.x_lnno)
88 #endif
89 #ifndef GET_LNSZ_SIZE
90 #define GET_LNSZ_SIZE(abfd, ext) bfd_h_get_16(abfd, (bfd_byte *) ext->x_sym.x_misc.x_lnsz.x_size)
91 #endif
92 #ifndef PUT_LNSZ_LNNO
93 #define PUT_LNSZ_LNNO(abfd, in, ext) bfd_h_put_16(abfd, in, (bfd_byte *)ext->x_sym.x_misc.x_lnsz.x_lnno)
94 #endif
95 #ifndef PUT_LNSZ_SIZE
96 #define PUT_LNSZ_SIZE(abfd, in, ext) bfd_h_put_16(abfd, in, (bfd_byte*) ext->x_sym.x_misc.x_lnsz.x_size)
97 #endif
98 #ifndef GET_SCN_SCNLEN
99 #define GET_SCN_SCNLEN(abfd,  ext) bfd_h_get_32(abfd, (bfd_byte *) ext->x_scn.x_scnlen)
100 #endif
101 #ifndef GET_SCN_NRELOC
102 #define GET_SCN_NRELOC(abfd,  ext) bfd_h_get_16(abfd, (bfd_byte *)ext->x_scn.x_nreloc)
103 #endif
104 #ifndef GET_SCN_NLINNO
105 #define GET_SCN_NLINNO(abfd, ext)  bfd_h_get_16(abfd, (bfd_byte *)ext->x_scn.x_nlinno)
106 #endif
107 #ifndef PUT_SCN_SCNLEN
108 #define PUT_SCN_SCNLEN(abfd,in, ext) bfd_h_put_32(abfd, in, (bfd_byte *) ext->x_scn.x_scnlen)
109 #endif
110 #ifndef PUT_SCN_NRELOC
111 #define PUT_SCN_NRELOC(abfd,in, ext) bfd_h_put_16(abfd, in, (bfd_byte *)ext->x_scn.x_nreloc)
112 #endif
113 #ifndef PUT_SCN_NLINNO
114 #define PUT_SCN_NLINNO(abfd,in, ext)  bfd_h_put_16(abfd,in, (bfd_byte  *) ext->x_scn.x_nlinno)
115 #endif
116 #ifndef GET_LINENO_LNNO
117 #define GET_LINENO_LNNO(abfd, ext) bfd_h_get_16(abfd, (bfd_byte *) (ext->l_lnno));
118 #endif
119 #ifndef PUT_LINENO_LNNO
120 #define PUT_LINENO_LNNO(abfd,val, ext) bfd_h_put_16(abfd,val,  (bfd_byte *) (ext->l_lnno));
121 #endif
122
123 /* The f_symptr field in the filehdr is sometimes 64 bits.  */
124 #ifndef GET_FILEHDR_SYMPTR
125 #define GET_FILEHDR_SYMPTR bfd_h_get_32
126 #endif
127 #ifndef PUT_FILEHDR_SYMPTR
128 #define PUT_FILEHDR_SYMPTR bfd_h_put_32
129 #endif
130
131 /* Some fields in the aouthdr are sometimes 64 bits.  */
132 #ifndef GET_AOUTHDR_TSIZE
133 #define GET_AOUTHDR_TSIZE bfd_h_get_32
134 #endif
135 #ifndef PUT_AOUTHDR_TSIZE
136 #define PUT_AOUTHDR_TSIZE bfd_h_put_32
137 #endif
138 #ifndef GET_AOUTHDR_DSIZE
139 #define GET_AOUTHDR_DSIZE bfd_h_get_32
140 #endif
141 #ifndef PUT_AOUTHDR_DSIZE
142 #define PUT_AOUTHDR_DSIZE bfd_h_put_32
143 #endif
144 #ifndef GET_AOUTHDR_BSIZE
145 #define GET_AOUTHDR_BSIZE bfd_h_get_32
146 #endif
147 #ifndef PUT_AOUTHDR_BSIZE
148 #define PUT_AOUTHDR_BSIZE bfd_h_put_32
149 #endif
150 #ifndef GET_AOUTHDR_ENTRY
151 #define GET_AOUTHDR_ENTRY bfd_h_get_32
152 #endif
153 #ifndef PUT_AOUTHDR_ENTRY
154 #define PUT_AOUTHDR_ENTRY bfd_h_put_32
155 #endif
156 #ifndef GET_AOUTHDR_TEXT_START
157 #define GET_AOUTHDR_TEXT_START bfd_h_get_32
158 #endif
159 #ifndef PUT_AOUTHDR_TEXT_START
160 #define PUT_AOUTHDR_TEXT_START bfd_h_put_32
161 #endif
162 #ifndef GET_AOUTHDR_DATA_START
163 #define GET_AOUTHDR_DATA_START bfd_h_get_32
164 #endif
165 #ifndef PUT_AOUTHDR_DATA_START
166 #define PUT_AOUTHDR_DATA_START bfd_h_put_32
167 #endif
168
169 /* Some fields in the scnhdr are sometimes 64 bits.  */
170 #ifndef GET_SCNHDR_PADDR
171 #define GET_SCNHDR_PADDR bfd_h_get_32
172 #endif
173 #ifndef PUT_SCNHDR_PADDR
174 #define PUT_SCNHDR_PADDR bfd_h_put_32
175 #endif
176 #ifndef GET_SCNHDR_VADDR
177 #define GET_SCNHDR_VADDR bfd_h_get_32
178 #endif
179 #ifndef PUT_SCNHDR_VADDR
180 #define PUT_SCNHDR_VADDR bfd_h_put_32
181 #endif
182 #ifndef GET_SCNHDR_SIZE
183 #define GET_SCNHDR_SIZE bfd_h_get_32
184 #endif
185 #ifndef PUT_SCNHDR_SIZE
186 #define PUT_SCNHDR_SIZE bfd_h_put_32
187 #endif
188 #ifndef GET_SCNHDR_SCNPTR
189 #define GET_SCNHDR_SCNPTR bfd_h_get_32
190 #endif
191 #ifndef PUT_SCNHDR_SCNPTR
192 #define PUT_SCNHDR_SCNPTR bfd_h_put_32
193 #endif
194 #ifndef GET_SCNHDR_RELPTR
195 #define GET_SCNHDR_RELPTR bfd_h_get_32
196 #endif
197 #ifndef PUT_SCNHDR_RELPTR
198 #define PUT_SCNHDR_RELPTR bfd_h_put_32
199 #endif
200 #ifndef GET_SCNHDR_LNNOPTR
201 #define GET_SCNHDR_LNNOPTR bfd_h_get_32
202 #endif
203 #ifndef PUT_SCNHDR_LNNOPTR
204 #define PUT_SCNHDR_LNNOPTR bfd_h_put_32
205 #endif
206
207 static void coff_swap_reloc_in PARAMS ((bfd *, PTR, PTR));
208 static unsigned int coff_swap_reloc_out PARAMS ((bfd *, PTR, PTR));
209 static void coff_swap_filehdr_in PARAMS ((bfd *, PTR, PTR));
210 static unsigned int coff_swap_filehdr_out PARAMS ((bfd *, PTR, PTR));
211 static void coff_swap_sym_in PARAMS ((bfd *, PTR, PTR));
212 static unsigned int coff_swap_sym_out PARAMS ((bfd *, PTR, PTR));
213 static void coff_swap_aux_in PARAMS ((bfd *, PTR, int, int, int, int, PTR));
214 static unsigned int coff_swap_aux_out
215   PARAMS ((bfd *, PTR, int, int, int, int, PTR));
216 static void coff_swap_lineno_in PARAMS ((bfd *, PTR, PTR));
217 static unsigned int coff_swap_lineno_out PARAMS ((bfd *, PTR, PTR));
218 static void coff_swap_aouthdr_in PARAMS ((bfd *, PTR, PTR));
219 static void add_data_entry
220   PARAMS ((bfd *, struct internal_extra_pe_aouthdr *, int, char *, bfd_vma));
221 static unsigned int coff_swap_aouthdr_out PARAMS ((bfd *, PTR, PTR));
222 static void coff_swap_scnhdr_in PARAMS ((bfd *, PTR, PTR));
223 static unsigned int coff_swap_scnhdr_out PARAMS ((bfd *, PTR, PTR));
224 static boolean pe_print_idata PARAMS ((bfd *, PTR));
225 static boolean pe_print_edata PARAMS ((bfd *, PTR));
226 static boolean pe_print_pdata PARAMS ((bfd *, PTR));
227 static boolean pe_print_reloc PARAMS ((bfd *, PTR));
228 static boolean pe_print_private_bfd_data PARAMS ((bfd *, PTR));
229 static boolean pe_mkobject PARAMS ((bfd *));
230 static PTR pe_mkobject_hook PARAMS ((bfd *, PTR, PTR));
231 static boolean pe_bfd_copy_private_bfd_data PARAMS ((bfd *, bfd *));
232
233 /**********************************************************************/
234
235 static void
236 coff_swap_reloc_in (abfd, src, dst)
237      bfd *abfd;
238      PTR src;
239      PTR dst;
240 {
241   RELOC *reloc_src = (RELOC *) src;
242   struct internal_reloc *reloc_dst = (struct internal_reloc *) dst;
243
244   reloc_dst->r_vaddr = bfd_h_get_32(abfd, (bfd_byte *)reloc_src->r_vaddr);
245   reloc_dst->r_symndx = bfd_h_get_signed_32(abfd, (bfd_byte *) reloc_src->r_symndx);
246
247   reloc_dst->r_type = bfd_h_get_16(abfd, (bfd_byte *) reloc_src->r_type);
248
249 #ifdef SWAP_IN_RELOC_OFFSET
250   reloc_dst->r_offset = SWAP_IN_RELOC_OFFSET(abfd,
251                                              (bfd_byte *) reloc_src->r_offset);
252 #endif
253 }
254
255
256 static unsigned int
257 coff_swap_reloc_out (abfd, src, dst)
258      bfd       *abfd;
259      PTR        src;
260      PTR        dst;
261 {
262   struct internal_reloc *reloc_src = (struct internal_reloc *)src;
263   struct external_reloc *reloc_dst = (struct external_reloc *)dst;
264   bfd_h_put_32(abfd, reloc_src->r_vaddr, (bfd_byte *) reloc_dst->r_vaddr);
265   bfd_h_put_32(abfd, reloc_src->r_symndx, (bfd_byte *) reloc_dst->r_symndx);
266
267   bfd_h_put_16(abfd, reloc_src->r_type, (bfd_byte *)
268                reloc_dst->r_type);
269
270 #ifdef SWAP_OUT_RELOC_OFFSET
271   SWAP_OUT_RELOC_OFFSET(abfd,
272                         reloc_src->r_offset,
273                         (bfd_byte *) reloc_dst->r_offset);
274 #endif
275 #ifdef SWAP_OUT_RELOC_EXTRA
276   SWAP_OUT_RELOC_EXTRA(abfd,reloc_src, reloc_dst);
277 #endif
278   return RELSZ;
279 }
280
281
282 static void
283 coff_swap_filehdr_in (abfd, src, dst)
284      bfd            *abfd;
285      PTR             src;
286      PTR             dst;
287 {
288   FILHDR *filehdr_src = (FILHDR *) src;
289   struct internal_filehdr *filehdr_dst = (struct internal_filehdr *) dst;
290   filehdr_dst->f_magic = bfd_h_get_16(abfd, (bfd_byte *) filehdr_src->f_magic);
291   filehdr_dst->f_nscns = bfd_h_get_16(abfd, (bfd_byte *)filehdr_src-> f_nscns);
292   filehdr_dst->f_timdat = bfd_h_get_32(abfd, (bfd_byte *)filehdr_src-> f_timdat);
293
294   filehdr_dst->f_nsyms = bfd_h_get_32(abfd, (bfd_byte *)filehdr_src-> f_nsyms);
295   filehdr_dst->f_flags = bfd_h_get_16(abfd, (bfd_byte *)filehdr_src-> f_flags);
296   filehdr_dst->f_symptr = bfd_h_get_32 (abfd, (bfd_byte *) filehdr_src->f_symptr);
297
298   /* Other people's tools sometimes generate headers with an nsyms but
299      a zero symptr.  */
300   if (filehdr_dst->f_nsyms != 0 && filehdr_dst->f_symptr == 0)
301     {
302       filehdr_dst->f_nsyms = 0;
303       filehdr_dst->f_flags |= F_LSYMS;
304     }
305
306   filehdr_dst->f_opthdr = bfd_h_get_16(abfd, 
307                                        (bfd_byte *)filehdr_src-> f_opthdr);
308 }
309
310 #ifdef COFF_IMAGE_WITH_PE
311
312 static  unsigned int
313 coff_swap_filehdr_out (abfd, in, out)
314      bfd       *abfd;
315      PTR        in;
316      PTR        out;
317 {
318   int idx;
319   struct internal_filehdr *filehdr_in = (struct internal_filehdr *)in;
320   FILHDR *filehdr_out = (FILHDR *)out;
321
322   if (pe_data (abfd)->has_reloc_section)
323     filehdr_in->f_flags &= ~F_RELFLG;
324
325   if (pe_data (abfd)->dll)
326     filehdr_in->f_flags |= F_DLL;
327
328   filehdr_in->pe.e_magic    = DOSMAGIC;
329   filehdr_in->pe.e_cblp     = 0x90;
330   filehdr_in->pe.e_cp       = 0x3;
331   filehdr_in->pe.e_crlc     = 0x0;
332   filehdr_in->pe.e_cparhdr  = 0x4;
333   filehdr_in->pe.e_minalloc = 0x0;
334   filehdr_in->pe.e_maxalloc = 0xffff;
335   filehdr_in->pe.e_ss       = 0x0;
336   filehdr_in->pe.e_sp       = 0xb8;
337   filehdr_in->pe.e_csum     = 0x0;
338   filehdr_in->pe.e_ip       = 0x0;
339   filehdr_in->pe.e_cs       = 0x0;
340   filehdr_in->pe.e_lfarlc   = 0x40;
341   filehdr_in->pe.e_ovno     = 0x0;
342
343   for (idx=0; idx < 4; idx++)
344     filehdr_in->pe.e_res[idx] = 0x0;
345
346   filehdr_in->pe.e_oemid   = 0x0;
347   filehdr_in->pe.e_oeminfo = 0x0;
348
349   for (idx=0; idx < 10; idx++)
350     filehdr_in->pe.e_res2[idx] = 0x0;
351
352   filehdr_in->pe.e_lfanew = 0x80;
353
354   /* this next collection of data are mostly just characters.  It appears
355      to be constant within the headers put on NT exes */
356   filehdr_in->pe.dos_message[0]  = 0x0eba1f0e;
357   filehdr_in->pe.dos_message[1]  = 0xcd09b400;
358   filehdr_in->pe.dos_message[2]  = 0x4c01b821;
359   filehdr_in->pe.dos_message[3]  = 0x685421cd;
360   filehdr_in->pe.dos_message[4]  = 0x70207369;
361   filehdr_in->pe.dos_message[5]  = 0x72676f72;
362   filehdr_in->pe.dos_message[6]  = 0x63206d61;
363   filehdr_in->pe.dos_message[7]  = 0x6f6e6e61;
364   filehdr_in->pe.dos_message[8]  = 0x65622074;
365   filehdr_in->pe.dos_message[9]  = 0x6e757220;
366   filehdr_in->pe.dos_message[10] = 0x206e6920;
367   filehdr_in->pe.dos_message[11] = 0x20534f44;
368   filehdr_in->pe.dos_message[12] = 0x65646f6d;
369   filehdr_in->pe.dos_message[13] = 0x0a0d0d2e;
370   filehdr_in->pe.dos_message[14] = 0x24;
371   filehdr_in->pe.dos_message[15] = 0x0;
372   filehdr_in->pe.nt_signature = NT_SIGNATURE;
373
374
375
376   bfd_h_put_16(abfd, filehdr_in->f_magic, (bfd_byte *) filehdr_out->f_magic);
377   bfd_h_put_16(abfd, filehdr_in->f_nscns, (bfd_byte *) filehdr_out->f_nscns);
378
379   bfd_h_put_32(abfd, time (0), (bfd_byte *) filehdr_out->f_timdat);
380   PUT_FILEHDR_SYMPTR (abfd, (bfd_vma) filehdr_in->f_symptr,
381                       (bfd_byte *) filehdr_out->f_symptr);
382   bfd_h_put_32(abfd, filehdr_in->f_nsyms, (bfd_byte *) filehdr_out->f_nsyms);
383   bfd_h_put_16(abfd, filehdr_in->f_opthdr, (bfd_byte *) filehdr_out->f_opthdr);
384   bfd_h_put_16(abfd, filehdr_in->f_flags, (bfd_byte *) filehdr_out->f_flags);
385
386   /* put in extra dos header stuff.  This data remains essentially
387      constant, it just has to be tacked on to the beginning of all exes 
388      for NT */
389   bfd_h_put_16(abfd, filehdr_in->pe.e_magic, (bfd_byte *) filehdr_out->e_magic);
390   bfd_h_put_16(abfd, filehdr_in->pe.e_cblp, (bfd_byte *) filehdr_out->e_cblp);
391   bfd_h_put_16(abfd, filehdr_in->pe.e_cp, (bfd_byte *) filehdr_out->e_cp);
392   bfd_h_put_16(abfd, filehdr_in->pe.e_crlc, (bfd_byte *) filehdr_out->e_crlc);
393   bfd_h_put_16(abfd, filehdr_in->pe.e_cparhdr, 
394                (bfd_byte *) filehdr_out->e_cparhdr);
395   bfd_h_put_16(abfd, filehdr_in->pe.e_minalloc, 
396                (bfd_byte *) filehdr_out->e_minalloc);
397   bfd_h_put_16(abfd, filehdr_in->pe.e_maxalloc, 
398                (bfd_byte *) filehdr_out->e_maxalloc);
399   bfd_h_put_16(abfd, filehdr_in->pe.e_ss, (bfd_byte *) filehdr_out->e_ss);
400   bfd_h_put_16(abfd, filehdr_in->pe.e_sp, (bfd_byte *) filehdr_out->e_sp);
401   bfd_h_put_16(abfd, filehdr_in->pe.e_csum, (bfd_byte *) filehdr_out->e_csum);
402   bfd_h_put_16(abfd, filehdr_in->pe.e_ip, (bfd_byte *) filehdr_out->e_ip);
403   bfd_h_put_16(abfd, filehdr_in->pe.e_cs, (bfd_byte *) filehdr_out->e_cs);
404   bfd_h_put_16(abfd, filehdr_in->pe.e_lfarlc, (bfd_byte *) filehdr_out->e_lfarlc);
405   bfd_h_put_16(abfd, filehdr_in->pe.e_ovno, (bfd_byte *) filehdr_out->e_ovno);
406   {
407     int idx;
408     for (idx=0; idx < 4; idx++)
409       bfd_h_put_16(abfd, filehdr_in->pe.e_res[idx], 
410                    (bfd_byte *) filehdr_out->e_res[idx]);
411   }
412   bfd_h_put_16(abfd, filehdr_in->pe.e_oemid, (bfd_byte *) filehdr_out->e_oemid);
413   bfd_h_put_16(abfd, filehdr_in->pe.e_oeminfo,
414                (bfd_byte *) filehdr_out->e_oeminfo);
415   {
416     int idx;
417     for (idx=0; idx < 10; idx++)
418       bfd_h_put_16(abfd, filehdr_in->pe.e_res2[idx],
419                    (bfd_byte *) filehdr_out->e_res2[idx]);
420   }
421   bfd_h_put_32(abfd, filehdr_in->pe.e_lfanew, (bfd_byte *) filehdr_out->e_lfanew);
422
423   {
424     int idx;
425     for (idx=0; idx < 16; idx++)
426       bfd_h_put_32(abfd, filehdr_in->pe.dos_message[idx],
427                    (bfd_byte *) filehdr_out->dos_message[idx]);
428   }
429
430   /* also put in the NT signature */
431   bfd_h_put_32(abfd, filehdr_in->pe.nt_signature, 
432                (bfd_byte *) filehdr_out->nt_signature);
433
434
435
436
437   return FILHSZ;
438 }
439 #else
440
441 static  unsigned int
442 coff_swap_filehdr_out (abfd, in, out)
443      bfd       *abfd;
444      PTR        in;
445      PTR        out;
446 {
447   struct internal_filehdr *filehdr_in = (struct internal_filehdr *)in;
448   FILHDR *filehdr_out = (FILHDR *)out;
449
450   bfd_h_put_16(abfd, filehdr_in->f_magic, (bfd_byte *) filehdr_out->f_magic);
451   bfd_h_put_16(abfd, filehdr_in->f_nscns, (bfd_byte *) filehdr_out->f_nscns);
452   bfd_h_put_32(abfd, filehdr_in->f_timdat, (bfd_byte *) filehdr_out->f_timdat);
453   PUT_FILEHDR_SYMPTR (abfd, (bfd_vma) filehdr_in->f_symptr,
454                       (bfd_byte *) filehdr_out->f_symptr);
455   bfd_h_put_32(abfd, filehdr_in->f_nsyms, (bfd_byte *) filehdr_out->f_nsyms);
456   bfd_h_put_16(abfd, filehdr_in->f_opthdr, (bfd_byte *) filehdr_out->f_opthdr);
457   bfd_h_put_16(abfd, filehdr_in->f_flags, (bfd_byte *) filehdr_out->f_flags);
458
459   return FILHSZ;
460 }
461
462 #endif
463
464
465 static void
466 coff_swap_sym_in (abfd, ext1, in1)
467      bfd            *abfd;
468      PTR ext1;
469      PTR in1;
470 {
471   SYMENT *ext = (SYMENT *)ext1;
472   struct internal_syment      *in = (struct internal_syment *)in1;
473
474   if( ext->e.e_name[0] == 0) {
475     in->_n._n_n._n_zeroes = 0;
476     in->_n._n_n._n_offset = bfd_h_get_32(abfd, (bfd_byte *) ext->e.e.e_offset);
477   }
478   else {
479 #if SYMNMLEN != E_SYMNMLEN
480     -> Error, we need to cope with truncating or extending SYMNMLEN!;
481 #else
482     memcpy(in->_n._n_name, ext->e.e_name, SYMNMLEN);
483 #endif
484   }
485
486   in->n_value = bfd_h_get_32(abfd, (bfd_byte *) ext->e_value); 
487   in->n_scnum = bfd_h_get_16(abfd, (bfd_byte *) ext->e_scnum);
488   if (sizeof(ext->e_type) == 2){
489     in->n_type = bfd_h_get_16(abfd, (bfd_byte *) ext->e_type);
490   }
491   else {
492     in->n_type = bfd_h_get_32(abfd, (bfd_byte *) ext->e_type);
493   }
494   in->n_sclass = bfd_h_get_8(abfd, ext->e_sclass);
495   in->n_numaux = bfd_h_get_8(abfd, ext->e_numaux);
496
497   /* The section symbols for the .idata$ sections have class 0x68
498      (C_SECTION), which MS documentation indicates is a section
499      symbol.  Unfortunately, the value field in the symbol is simply a
500      copy of the .idata section's flags rather than something useful.
501      When these symbols are encountered, change the value to 0 so that
502      they will be handled somewhat correctly in the bfd code.  */
503   if (in->n_sclass == C_SECTION)
504     {
505       in->n_value = 0x0;
506
507 #if 0
508       /* FIXME: This is clearly wrong.  The problem seems to be that
509          undefined C_SECTION symbols appear in the first object of a
510          MS generated .lib file, and the symbols are not defined
511          anywhere.  */
512       in->n_scnum = 1;
513
514       /* I have tried setting the class to 3 and using the following
515          to set the section number.  This will put the address of the
516          pointer to the string kernel32.dll at addresses 0 and 0x10
517          off start of idata section which is not correct */
518       /*    if (strcmp (in->_n._n_name, ".idata$4") == 0) */
519       /*      in->n_scnum = 3; */
520       /*    else */
521       /*      in->n_scnum = 2; */
522 #else
523       /* Create synthetic empty sections as needed.  DJ */
524       if (in->n_scnum == 0)
525         {
526           asection *sec;
527           for (sec=abfd->sections; sec; sec=sec->next)
528             {
529               if (strcmp (sec->name, in->n_name) == 0)
530                 {
531                   in->n_scnum = sec->target_index;
532                   break;
533                 }
534             }
535         }
536       if (in->n_scnum == 0)
537         {
538           int unused_section_number = 0;
539           asection *sec;
540           char *name;
541           for (sec=abfd->sections; sec; sec=sec->next)
542             if (unused_section_number <= sec->target_index)
543               unused_section_number = sec->target_index+1;
544
545           name = bfd_alloc (abfd, strlen (in->n_name) + 10);
546           if (name == NULL)
547             return;
548           strcpy (name, in->n_name);
549           sec = bfd_make_section_anyway (abfd, name);
550
551           sec->vma = 0;
552           sec->lma = 0;
553           sec->_cooked_size = 0;
554           sec->_raw_size = 0;
555           sec->filepos = 0;
556           sec->rel_filepos = 0;
557           sec->reloc_count = 0;
558           sec->line_filepos = 0;
559           sec->lineno_count = 0;
560           sec->userdata = NULL;
561           sec->next = (asection *) NULL;
562           sec->flags = 0;
563           sec->alignment_power = 2;
564           sec->flags = SEC_HAS_CONTENTS | SEC_ALLOC | SEC_DATA | SEC_LOAD;
565
566           sec->target_index = unused_section_number;
567
568           in->n_scnum = unused_section_number;
569         }
570       in->n_sclass = C_STAT;
571 #endif
572     }
573
574 #ifdef coff_swap_sym_in_hook
575   coff_swap_sym_in_hook(abfd, ext1, in1);
576 #endif
577 }
578
579 static unsigned int
580 coff_swap_sym_out (abfd, inp, extp)
581      bfd       *abfd;
582      PTR        inp;
583      PTR        extp;
584 {
585   struct internal_syment *in = (struct internal_syment *)inp;
586   SYMENT *ext =(SYMENT *)extp;
587   if(in->_n._n_name[0] == 0) {
588     bfd_h_put_32(abfd, 0, (bfd_byte *) ext->e.e.e_zeroes);
589     bfd_h_put_32(abfd, in->_n._n_n._n_offset, (bfd_byte *)  ext->e.e.e_offset);
590   }
591   else {
592 #if SYMNMLEN != E_SYMNMLEN
593     -> Error, we need to cope with truncating or extending SYMNMLEN!;
594 #else
595     memcpy(ext->e.e_name, in->_n._n_name, SYMNMLEN);
596 #endif
597   }
598
599   bfd_h_put_32(abfd,  in->n_value , (bfd_byte *) ext->e_value);
600   bfd_h_put_16(abfd,  in->n_scnum , (bfd_byte *) ext->e_scnum);
601   if (sizeof(ext->e_type) == 2)
602     {
603       bfd_h_put_16(abfd,  in->n_type , (bfd_byte *) ext->e_type);
604     }
605   else
606     {
607       bfd_h_put_32(abfd,  in->n_type , (bfd_byte *) ext->e_type);
608     }
609   bfd_h_put_8(abfd,  in->n_sclass , ext->e_sclass);
610   bfd_h_put_8(abfd,  in->n_numaux , ext->e_numaux);
611
612   return SYMESZ;
613 }
614
615 static void
616 coff_swap_aux_in (abfd, ext1, type, class, indx, numaux, in1)
617      bfd            *abfd;
618      PTR              ext1;
619      int             type;
620      int             class;
621      int              indx;
622      int              numaux;
623      PTR              in1;
624 {
625   AUXENT    *ext = (AUXENT *)ext1;
626   union internal_auxent *in = (union internal_auxent *)in1;
627
628   switch (class) {
629   case C_FILE:
630     if (ext->x_file.x_fname[0] == 0) {
631       in->x_file.x_n.x_zeroes = 0;
632       in->x_file.x_n.x_offset = 
633         bfd_h_get_32(abfd, (bfd_byte *) ext->x_file.x_n.x_offset);
634     } else {
635 #if FILNMLEN != E_FILNMLEN
636       -> Error, we need to cope with truncating or extending FILNMLEN!;
637 #else
638       memcpy (in->x_file.x_fname, ext->x_file.x_fname, FILNMLEN);
639 #endif
640     }
641     return;
642
643
644   case C_STAT:
645 #ifdef C_LEAFSTAT
646   case C_LEAFSTAT:
647 #endif
648   case C_HIDDEN:
649     if (type == T_NULL) {
650       in->x_scn.x_scnlen = GET_SCN_SCNLEN(abfd, ext);
651       in->x_scn.x_nreloc = GET_SCN_NRELOC(abfd, ext);
652       in->x_scn.x_nlinno = GET_SCN_NLINNO(abfd, ext);
653       in->x_scn.x_checksum = bfd_h_get_32 (abfd,
654                                            (bfd_byte *) ext->x_scn.x_checksum);
655       in->x_scn.x_associated =
656         bfd_h_get_16 (abfd, (bfd_byte *) ext->x_scn.x_associated);
657       in->x_scn.x_comdat = bfd_h_get_8 (abfd,
658                                         (bfd_byte *) ext->x_scn.x_comdat);
659       return;
660     }
661     break;
662   }
663
664   in->x_sym.x_tagndx.l = bfd_h_get_32(abfd, (bfd_byte *) ext->x_sym.x_tagndx);
665 #ifndef NO_TVNDX
666   in->x_sym.x_tvndx = bfd_h_get_16(abfd, (bfd_byte *) ext->x_sym.x_tvndx);
667 #endif
668
669   if (class == C_BLOCK || class == C_FCN || ISFCN (type) || ISTAG (class))
670     {
671       in->x_sym.x_fcnary.x_fcn.x_lnnoptr = GET_FCN_LNNOPTR (abfd, ext);
672       in->x_sym.x_fcnary.x_fcn.x_endndx.l = GET_FCN_ENDNDX (abfd, ext);
673     }
674   else
675     {
676 #if DIMNUM != E_DIMNUM
677  #error we need to cope with truncating or extending DIMNUM
678 #endif
679       in->x_sym.x_fcnary.x_ary.x_dimen[0] =
680         bfd_h_get_16 (abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[0]);
681       in->x_sym.x_fcnary.x_ary.x_dimen[1] =
682         bfd_h_get_16 (abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[1]);
683       in->x_sym.x_fcnary.x_ary.x_dimen[2] =
684         bfd_h_get_16 (abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[2]);
685       in->x_sym.x_fcnary.x_ary.x_dimen[3] =
686         bfd_h_get_16 (abfd, (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[3]);
687     }
688
689   if (ISFCN(type)) {
690     in->x_sym.x_misc.x_fsize = bfd_h_get_32(abfd, (bfd_byte *) ext->x_sym.x_misc.x_fsize);
691   }
692   else {
693     in->x_sym.x_misc.x_lnsz.x_lnno = GET_LNSZ_LNNO(abfd, ext);
694     in->x_sym.x_misc.x_lnsz.x_size = GET_LNSZ_SIZE(abfd, ext);
695   }
696 }
697
698 static unsigned int
699 coff_swap_aux_out (abfd, inp, type, class, indx, numaux, extp)
700      bfd   *abfd;
701      PTR        inp;
702      int   type;
703      int   class;
704      int   indx;
705      int   numaux;
706      PTR        extp;
707 {
708   union internal_auxent *in = (union internal_auxent *)inp;
709   AUXENT *ext = (AUXENT *)extp;
710
711   memset((PTR)ext, 0, AUXESZ);
712   switch (class) {
713   case C_FILE:
714     if (in->x_file.x_fname[0] == 0) {
715       bfd_h_put_32(abfd, 0, (bfd_byte *) ext->x_file.x_n.x_zeroes);
716       bfd_h_put_32(abfd,
717               in->x_file.x_n.x_offset,
718               (bfd_byte *) ext->x_file.x_n.x_offset);
719     }
720     else {
721 #if FILNMLEN != E_FILNMLEN
722       -> Error, we need to cope with truncating or extending FILNMLEN!;
723 #else
724       memcpy (ext->x_file.x_fname, in->x_file.x_fname, FILNMLEN);
725 #endif
726     }
727     return AUXESZ;
728
729
730   case C_STAT:
731 #ifdef C_LEAFSTAT
732   case C_LEAFSTAT:
733 #endif
734   case C_HIDDEN:
735     if (type == T_NULL) {
736       PUT_SCN_SCNLEN(abfd, in->x_scn.x_scnlen, ext);
737       PUT_SCN_NRELOC(abfd, in->x_scn.x_nreloc, ext);
738       PUT_SCN_NLINNO(abfd, in->x_scn.x_nlinno, ext);
739       bfd_h_put_32 (abfd, in->x_scn.x_checksum,
740                     (bfd_byte *) ext->x_scn.x_checksum);
741       bfd_h_put_16 (abfd, in->x_scn.x_associated,
742                     (bfd_byte *) ext->x_scn.x_associated);
743       bfd_h_put_8 (abfd, in->x_scn.x_comdat,
744                    (bfd_byte *) ext->x_scn.x_comdat);
745       return AUXESZ;
746     }
747     break;
748   }
749
750   bfd_h_put_32(abfd, in->x_sym.x_tagndx.l, (bfd_byte *) ext->x_sym.x_tagndx);
751 #ifndef NO_TVNDX
752   bfd_h_put_16(abfd, in->x_sym.x_tvndx , (bfd_byte *) ext->x_sym.x_tvndx);
753 #endif
754
755   if (class == C_BLOCK || class == C_FCN || ISFCN (type) || ISTAG (class))
756     {
757       PUT_FCN_LNNOPTR(abfd,  in->x_sym.x_fcnary.x_fcn.x_lnnoptr, ext);
758       PUT_FCN_ENDNDX(abfd,  in->x_sym.x_fcnary.x_fcn.x_endndx.l, ext);
759     }
760   else
761     {
762 #if DIMNUM != E_DIMNUM
763  #error we need to cope with truncating or extending DIMNUM
764 #endif
765       bfd_h_put_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[0],
766                     (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[0]);
767       bfd_h_put_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[1],
768                     (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[1]);
769       bfd_h_put_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[2],
770                     (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[2]);
771       bfd_h_put_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[3],
772                     (bfd_byte *) ext->x_sym.x_fcnary.x_ary.x_dimen[3]);
773     }
774
775   if (ISFCN (type))
776     bfd_h_put_32 (abfd, in->x_sym.x_misc.x_fsize,
777              (bfd_byte *)  ext->x_sym.x_misc.x_fsize);
778   else
779     {
780       PUT_LNSZ_LNNO (abfd, in->x_sym.x_misc.x_lnsz.x_lnno, ext);
781       PUT_LNSZ_SIZE (abfd, in->x_sym.x_misc.x_lnsz.x_size, ext);
782     }
783
784   return AUXESZ;
785 }
786
787
788 static void
789 coff_swap_lineno_in (abfd, ext1, in1)
790      bfd            *abfd;
791      PTR ext1;
792      PTR in1;
793 {
794   LINENO *ext = (LINENO *)ext1;
795   struct internal_lineno      *in = (struct internal_lineno *)in1;
796
797   in->l_addr.l_symndx = bfd_h_get_32(abfd, (bfd_byte *) ext->l_addr.l_symndx);
798   in->l_lnno = GET_LINENO_LNNO(abfd, ext);
799 }
800
801 static unsigned int
802 coff_swap_lineno_out (abfd, inp, outp)
803      bfd       *abfd;
804      PTR        inp;
805      PTR        outp;
806 {
807   struct internal_lineno *in = (struct internal_lineno *)inp;
808   struct external_lineno *ext = (struct external_lineno *)outp;
809   bfd_h_put_32(abfd, in->l_addr.l_symndx, (bfd_byte *)
810           ext->l_addr.l_symndx);
811
812   PUT_LINENO_LNNO (abfd, in->l_lnno, ext);
813   return LINESZ;
814 }
815
816
817
818 static void
819 coff_swap_aouthdr_in (abfd, aouthdr_ext1, aouthdr_int1)
820      bfd            *abfd;
821      PTR aouthdr_ext1;
822      PTR aouthdr_int1;
823 {
824   struct internal_extra_pe_aouthdr *a;
825   PEAOUTHDR *src = (PEAOUTHDR *)(aouthdr_ext1);
826   AOUTHDR        *aouthdr_ext = (AOUTHDR *) aouthdr_ext1;
827   struct internal_aouthdr *aouthdr_int = (struct internal_aouthdr *)aouthdr_int1;
828
829   aouthdr_int->magic = bfd_h_get_16(abfd, (bfd_byte *) aouthdr_ext->magic);
830   aouthdr_int->vstamp = bfd_h_get_16(abfd, (bfd_byte *) aouthdr_ext->vstamp);
831   aouthdr_int->tsize =
832     GET_AOUTHDR_TSIZE (abfd, (bfd_byte *) aouthdr_ext->tsize);
833   aouthdr_int->dsize =
834     GET_AOUTHDR_DSIZE (abfd, (bfd_byte *) aouthdr_ext->dsize);
835   aouthdr_int->bsize =
836     GET_AOUTHDR_BSIZE (abfd, (bfd_byte *) aouthdr_ext->bsize);
837   aouthdr_int->entry =
838     GET_AOUTHDR_ENTRY (abfd, (bfd_byte *) aouthdr_ext->entry);
839   aouthdr_int->text_start =
840     GET_AOUTHDR_TEXT_START (abfd, (bfd_byte *) aouthdr_ext->text_start);
841   aouthdr_int->data_start =
842     GET_AOUTHDR_DATA_START (abfd, (bfd_byte *) aouthdr_ext->data_start);
843
844   a = &aouthdr_int->pe;
845   a->ImageBase = bfd_h_get_32 (abfd, (bfd_byte *) src->ImageBase);
846   a->SectionAlignment = bfd_h_get_32 (abfd, (bfd_byte *) src->SectionAlignment);
847   a->FileAlignment = bfd_h_get_32 (abfd, (bfd_byte *) src->FileAlignment);
848   a->MajorOperatingSystemVersion = 
849     bfd_h_get_16 (abfd, (bfd_byte *) src->MajorOperatingSystemVersion);
850   a->MinorOperatingSystemVersion = 
851     bfd_h_get_16 (abfd, (bfd_byte *) src->MinorOperatingSystemVersion);
852   a->MajorImageVersion = bfd_h_get_16 (abfd, (bfd_byte *) src->MajorImageVersion);
853   a->MinorImageVersion = bfd_h_get_16 (abfd, (bfd_byte *) src->MinorImageVersion);
854   a->MajorSubsystemVersion = bfd_h_get_16 (abfd, (bfd_byte *) src->MajorSubsystemVersion);
855   a->MinorSubsystemVersion = bfd_h_get_16 (abfd, (bfd_byte *) src->MinorSubsystemVersion);
856   a->Reserved1 = bfd_h_get_32 (abfd, (bfd_byte *) src->Reserved1);
857   a->SizeOfImage = bfd_h_get_32 (abfd, (bfd_byte *) src->SizeOfImage);
858   a->SizeOfHeaders = bfd_h_get_32 (abfd, (bfd_byte *) src->SizeOfHeaders);
859   a->CheckSum = bfd_h_get_32 (abfd, (bfd_byte *) src->CheckSum);
860   a->Subsystem = bfd_h_get_16 (abfd, (bfd_byte *) src->Subsystem);
861   a->DllCharacteristics = bfd_h_get_16 (abfd, (bfd_byte *) src->DllCharacteristics);
862   a->SizeOfStackReserve = bfd_h_get_32 (abfd, (bfd_byte *) src->SizeOfStackReserve);
863   a->SizeOfStackCommit = bfd_h_get_32 (abfd, (bfd_byte *) src->SizeOfStackCommit);
864   a->SizeOfHeapReserve = bfd_h_get_32 (abfd, (bfd_byte *) src->SizeOfHeapReserve);
865   a->SizeOfHeapCommit = bfd_h_get_32 (abfd, (bfd_byte *) src->SizeOfHeapCommit);
866   a->LoaderFlags = bfd_h_get_32 (abfd, (bfd_byte *) src->LoaderFlags);
867   a->NumberOfRvaAndSizes = bfd_h_get_32 (abfd, (bfd_byte *) src->NumberOfRvaAndSizes);
868
869   {
870     int idx;
871     for (idx=0; idx < 16; idx++)
872       {
873         a->DataDirectory[idx].VirtualAddress =
874           bfd_h_get_32 (abfd, (bfd_byte *) src->DataDirectory[idx][0]);
875         a->DataDirectory[idx].Size =
876           bfd_h_get_32 (abfd, (bfd_byte *) src->DataDirectory[idx][1]);
877       }
878   }
879
880   if (aouthdr_int->entry)
881     {
882       aouthdr_int->entry += a->ImageBase;
883       aouthdr_int->entry &= 0xffffffff;
884     }
885   if (aouthdr_int->tsize) 
886     {
887       aouthdr_int->text_start += a->ImageBase;
888       aouthdr_int->text_start &= 0xffffffff;
889     }
890   if (aouthdr_int->dsize) 
891     {
892       aouthdr_int->data_start += a->ImageBase;
893       aouthdr_int->data_start &= 0xffffffff;
894     }
895
896 #ifdef POWERPC_LE_PE
897   /* These three fields are normally set up by ppc_relocate_section.
898      In the case of reading a file in, we can pick them up from
899      the DataDirectory.
900   */
901   first_thunk_address = a->DataDirectory[12].VirtualAddress ;
902   thunk_size = a->DataDirectory[12].Size;
903   import_table_size = a->DataDirectory[1].Size;
904 #endif
905 }
906
907
908 static void add_data_entry (abfd, aout, idx, name, base)
909      bfd *abfd;
910      struct internal_extra_pe_aouthdr *aout;
911      int idx;
912      char *name;
913      bfd_vma base;
914 {
915   asection *sec = bfd_get_section_by_name (abfd, name);
916
917   /* add import directory information if it exists */
918   if ((sec != NULL)
919       && (coff_section_data (abfd, sec) != NULL)
920       && (pei_section_data (abfd, sec) != NULL))
921     {
922       aout->DataDirectory[idx].VirtualAddress = (sec->vma - base) & 0xffffffff;
923       aout->DataDirectory[idx].Size = pei_section_data (abfd, sec)->virt_size;
924       sec->flags |= SEC_DATA;
925     }
926 }
927
928 static unsigned int
929 coff_swap_aouthdr_out (abfd, in, out)
930      bfd       *abfd;
931      PTR        in;
932      PTR        out;
933 {
934   struct internal_aouthdr *aouthdr_in = (struct internal_aouthdr *)in;
935   struct internal_extra_pe_aouthdr *extra = &pe_data (abfd)->pe_opthdr;
936   PEAOUTHDR *aouthdr_out = (PEAOUTHDR *)out;
937
938   bfd_vma sa = extra->SectionAlignment;
939   bfd_vma fa = extra->FileAlignment;
940   bfd_vma ib = extra->ImageBase ;
941
942   if (aouthdr_in->tsize) 
943     {
944       aouthdr_in->text_start -= ib;
945       aouthdr_in->text_start &= 0xffffffff;
946     }
947   if (aouthdr_in->dsize) 
948     {
949       aouthdr_in->data_start -= ib;
950       aouthdr_in->data_start &= 0xffffffff;
951     }
952   if (aouthdr_in->entry) 
953     {
954       aouthdr_in->entry -= ib;
955       aouthdr_in->entry &= 0xffffffff;
956     }
957
958 #define FA(x)  (((x) + fa -1 ) & (- fa))
959 #define SA(x)  (((x) + sa -1 ) & (- sa))
960
961   /* We like to have the sizes aligned */
962
963   aouthdr_in->bsize = FA (aouthdr_in->bsize);
964
965
966   extra->NumberOfRvaAndSizes = IMAGE_NUMBEROF_DIRECTORY_ENTRIES;
967
968   /* first null out all data directory entries .. */
969   memset (extra->DataDirectory, sizeof (extra->DataDirectory), 0);
970
971   add_data_entry (abfd, extra, 0, ".edata", ib);
972   add_data_entry (abfd, extra, 1, ".idata", ib);
973   add_data_entry (abfd, extra, 2, ".rsrc" ,ib);
974
975 #ifdef POWERPC_LE_PE
976   /* FIXME: do other PE platforms use this? */
977   add_data_entry (abfd, extra, 3, ".pdata" ,ib);
978 #endif
979
980   add_data_entry (abfd, extra, 5, ".reloc", ib);
981
982 #ifdef POWERPC_LE_PE
983   /* On the PPC NT system, this field is set up as follows. It is
984      not an "officially" reserved field, so it currently has no title.
985      first_thunk_address is idata$5, and the thunk_size is the size
986      of the idata$5 chunk of the idata section.
987   */
988   extra->DataDirectory[12].VirtualAddress = first_thunk_address;
989   extra->DataDirectory[12].Size = thunk_size;
990
991   /* On the PPC NT system, the size of the directory entry is not the
992      size of the entire section. It's actually offset to the end of 
993      the idata$3 component of the idata section. This is the size of
994      the entire import table. (also known as the start of idata$4)
995   */
996   extra->DataDirectory[1].Size = import_table_size;
997 #endif
998
999   {
1000     asection *sec;
1001     bfd_vma dsize= 0;
1002     bfd_vma isize = SA(abfd->sections->filepos);
1003     bfd_vma tsize= 0;
1004
1005     for (sec = abfd->sections; sec; sec = sec->next)
1006       {
1007         int rounded = FA(sec->_raw_size);
1008
1009         if (sec->flags & SEC_DATA) 
1010           dsize += rounded;
1011         if (sec->flags & SEC_CODE)
1012           tsize += rounded;
1013         isize += SA(rounded);
1014       }
1015
1016     aouthdr_in->dsize = dsize;
1017     aouthdr_in->tsize = tsize;
1018     extra->SizeOfImage = isize;
1019   }
1020
1021   extra->SizeOfHeaders = abfd->sections->filepos;
1022   bfd_h_put_16(abfd, aouthdr_in->magic, (bfd_byte *) aouthdr_out->standard.magic);
1023
1024 #ifdef POWERPC_LE_PE
1025   /* this little piece of magic sets the "linker version" field to 2.60 */
1026   bfd_h_put_16(abfd, 2  + 60 * 256, (bfd_byte *) aouthdr_out->standard.vstamp);
1027 #else
1028   /* this little piece of magic sets the "linker version" field to 2.55 */
1029   bfd_h_put_16(abfd, 2  + 55 * 256, (bfd_byte *) aouthdr_out->standard.vstamp);
1030 #endif
1031
1032   PUT_AOUTHDR_TSIZE (abfd, aouthdr_in->tsize, (bfd_byte *) aouthdr_out->standard.tsize);
1033   PUT_AOUTHDR_DSIZE (abfd, aouthdr_in->dsize, (bfd_byte *) aouthdr_out->standard.dsize);
1034   PUT_AOUTHDR_BSIZE (abfd, aouthdr_in->bsize, (bfd_byte *) aouthdr_out->standard.bsize);
1035   PUT_AOUTHDR_ENTRY (abfd, aouthdr_in->entry, (bfd_byte *) aouthdr_out->standard.entry);
1036   PUT_AOUTHDR_TEXT_START (abfd, aouthdr_in->text_start,
1037                           (bfd_byte *) aouthdr_out->standard.text_start);
1038
1039   PUT_AOUTHDR_DATA_START (abfd, aouthdr_in->data_start,
1040                           (bfd_byte *) aouthdr_out->standard.data_start);
1041
1042
1043   bfd_h_put_32 (abfd, extra->ImageBase, 
1044                 (bfd_byte *) aouthdr_out->ImageBase);
1045   bfd_h_put_32 (abfd, extra->SectionAlignment,
1046                 (bfd_byte *) aouthdr_out->SectionAlignment);
1047   bfd_h_put_32 (abfd, extra->FileAlignment,
1048                 (bfd_byte *) aouthdr_out->FileAlignment);
1049   bfd_h_put_16 (abfd, extra->MajorOperatingSystemVersion,
1050                 (bfd_byte *) aouthdr_out->MajorOperatingSystemVersion);
1051   bfd_h_put_16 (abfd, extra->MinorOperatingSystemVersion,
1052                 (bfd_byte *) aouthdr_out->MinorOperatingSystemVersion);
1053   bfd_h_put_16 (abfd, extra->MajorImageVersion,
1054                 (bfd_byte *) aouthdr_out->MajorImageVersion);
1055   bfd_h_put_16 (abfd, extra->MinorImageVersion,
1056                 (bfd_byte *) aouthdr_out->MinorImageVersion);
1057   bfd_h_put_16 (abfd, extra->MajorSubsystemVersion,
1058                 (bfd_byte *) aouthdr_out->MajorSubsystemVersion);
1059   bfd_h_put_16 (abfd, extra->MinorSubsystemVersion,
1060                 (bfd_byte *) aouthdr_out->MinorSubsystemVersion);
1061   bfd_h_put_32 (abfd, extra->Reserved1,
1062                 (bfd_byte *) aouthdr_out->Reserved1);
1063   bfd_h_put_32 (abfd, extra->SizeOfImage,
1064                 (bfd_byte *) aouthdr_out->SizeOfImage);
1065   bfd_h_put_32 (abfd, extra->SizeOfHeaders,
1066                 (bfd_byte *) aouthdr_out->SizeOfHeaders);
1067   bfd_h_put_32 (abfd, extra->CheckSum,
1068                 (bfd_byte *) aouthdr_out->CheckSum);
1069   bfd_h_put_16 (abfd, extra->Subsystem,
1070                 (bfd_byte *) aouthdr_out->Subsystem);
1071   bfd_h_put_16 (abfd, extra->DllCharacteristics,
1072                 (bfd_byte *) aouthdr_out->DllCharacteristics);
1073   bfd_h_put_32 (abfd, extra->SizeOfStackReserve,
1074                 (bfd_byte *) aouthdr_out->SizeOfStackReserve);
1075   bfd_h_put_32 (abfd, extra->SizeOfStackCommit,
1076                 (bfd_byte *) aouthdr_out->SizeOfStackCommit);
1077   bfd_h_put_32 (abfd, extra->SizeOfHeapReserve,
1078                 (bfd_byte *) aouthdr_out->SizeOfHeapReserve);
1079   bfd_h_put_32 (abfd, extra->SizeOfHeapCommit,
1080                 (bfd_byte *) aouthdr_out->SizeOfHeapCommit);
1081   bfd_h_put_32 (abfd, extra->LoaderFlags,
1082                 (bfd_byte *) aouthdr_out->LoaderFlags);
1083   bfd_h_put_32 (abfd, extra->NumberOfRvaAndSizes,
1084                 (bfd_byte *) aouthdr_out->NumberOfRvaAndSizes);
1085   {
1086     int idx;
1087     for (idx=0; idx < 16; idx++)
1088       {
1089         bfd_h_put_32 (abfd, extra->DataDirectory[idx].VirtualAddress,
1090                       (bfd_byte *) aouthdr_out->DataDirectory[idx][0]);
1091         bfd_h_put_32 (abfd, extra->DataDirectory[idx].Size,
1092                       (bfd_byte *) aouthdr_out->DataDirectory[idx][1]);
1093       }
1094   }
1095
1096   return AOUTSZ;
1097 }
1098
1099 static void
1100     coff_swap_scnhdr_in (abfd, ext, in)
1101       bfd            *abfd;
1102   PTR        ext;
1103   PTR        in;
1104 {
1105   SCNHDR *scnhdr_ext = (SCNHDR *) ext;
1106   struct internal_scnhdr *scnhdr_int = (struct internal_scnhdr *) in;
1107
1108   memcpy(scnhdr_int->s_name, scnhdr_ext->s_name, sizeof(scnhdr_int->s_name));
1109   scnhdr_int->s_vaddr =
1110     GET_SCNHDR_VADDR (abfd, (bfd_byte *) scnhdr_ext->s_vaddr);
1111   scnhdr_int->s_paddr =
1112     GET_SCNHDR_PADDR (abfd, (bfd_byte *) scnhdr_ext->s_paddr);
1113   scnhdr_int->s_size =
1114     GET_SCNHDR_SIZE (abfd, (bfd_byte *) scnhdr_ext->s_size);
1115   scnhdr_int->s_scnptr =
1116     GET_SCNHDR_SCNPTR (abfd, (bfd_byte *) scnhdr_ext->s_scnptr);
1117   scnhdr_int->s_relptr =
1118     GET_SCNHDR_RELPTR (abfd, (bfd_byte *) scnhdr_ext->s_relptr);
1119   scnhdr_int->s_lnnoptr =
1120     GET_SCNHDR_LNNOPTR (abfd, (bfd_byte *) scnhdr_ext->s_lnnoptr);
1121   scnhdr_int->s_flags = bfd_h_get_32(abfd, (bfd_byte *) scnhdr_ext->s_flags);
1122
1123   scnhdr_int->s_nreloc = bfd_h_get_16(abfd, (bfd_byte *) scnhdr_ext->s_nreloc);
1124   scnhdr_int->s_nlnno = bfd_h_get_16(abfd, (bfd_byte *) scnhdr_ext->s_nlnno);
1125
1126   if (scnhdr_int->s_vaddr != 0) 
1127     {
1128       scnhdr_int->s_vaddr += pe_data (abfd)->pe_opthdr.ImageBase;
1129       scnhdr_int->s_vaddr &= 0xffffffff;
1130     }
1131   if (strcmp (scnhdr_int->s_name, _BSS) == 0) 
1132     {
1133       scnhdr_int->s_size = scnhdr_int->s_paddr;
1134       scnhdr_int->s_paddr = 0;
1135     }
1136 }
1137
1138 static unsigned int
1139 coff_swap_scnhdr_out (abfd, in, out)
1140      bfd       *abfd;
1141      PTR        in;
1142      PTR        out;
1143 {
1144   struct internal_scnhdr *scnhdr_int = (struct internal_scnhdr *)in;
1145   SCNHDR *scnhdr_ext = (SCNHDR *)out;
1146   unsigned int ret = SCNHSZ;
1147   bfd_vma ps;
1148   bfd_vma ss;
1149
1150   memcpy(scnhdr_ext->s_name, scnhdr_int->s_name, sizeof(scnhdr_int->s_name));
1151
1152   PUT_SCNHDR_VADDR (abfd, 
1153                     ((scnhdr_int->s_vaddr 
1154                       - pe_data(abfd)->pe_opthdr.ImageBase)
1155                      & 0xffffffff),
1156                     (bfd_byte *) scnhdr_ext->s_vaddr);
1157
1158   /* NT wants the size data to be rounded up to the next NT_FILE_ALIGNMENT
1159      value except for the BSS section, its s_size should be 0 */
1160
1161
1162   if (strcmp (scnhdr_int->s_name, _BSS) == 0) 
1163     {
1164       ps = scnhdr_int->s_size;
1165       ss = 0;
1166     }
1167   else
1168     {
1169       ps = scnhdr_int->s_paddr;
1170       ss = scnhdr_int->s_size;
1171     }
1172
1173   PUT_SCNHDR_SIZE (abfd, ss,
1174                    (bfd_byte *) scnhdr_ext->s_size);
1175
1176
1177   PUT_SCNHDR_PADDR (abfd, ps, (bfd_byte *) scnhdr_ext->s_paddr);
1178
1179   PUT_SCNHDR_SCNPTR (abfd, scnhdr_int->s_scnptr,
1180                      (bfd_byte *) scnhdr_ext->s_scnptr);
1181   PUT_SCNHDR_RELPTR (abfd, scnhdr_int->s_relptr,
1182                      (bfd_byte *) scnhdr_ext->s_relptr);
1183   PUT_SCNHDR_LNNOPTR (abfd, scnhdr_int->s_lnnoptr,
1184                       (bfd_byte *) scnhdr_ext->s_lnnoptr);
1185
1186   /* Extra flags must be set when dealing with NT.  All sections should also
1187      have the IMAGE_SCN_MEM_READ (0x40000000) flag set.  In addition, the
1188      .text section must have IMAGE_SCN_MEM_EXECUTE (0x20000000) and the data
1189      sections (.idata, .data, .bss, .CRT) must have IMAGE_SCN_MEM_WRITE set
1190      (this is especially important when dealing with the .idata section since
1191      the addresses for routines from .dlls must be overwritten).  If .reloc
1192      section data is ever generated, we must add IMAGE_SCN_MEM_DISCARDABLE
1193      (0x02000000).  Also, the resource data should also be read and
1194      writable.  */
1195
1196   /* FIXME: alignment is also encoded in this field, at least on ppc (krk) */
1197   /* FIXME: even worse, I don't see how to get the original alignment field*/
1198   /*        back...                                                        */
1199
1200   /* FIXME: Basing this on section names is bogus.  Also, this should
1201      be in sec_to_styp_flags.  */
1202
1203   {
1204     int flags = scnhdr_int->s_flags;
1205     if (strcmp (scnhdr_int->s_name, ".data")  == 0 ||
1206         strcmp (scnhdr_int->s_name, ".CRT")   == 0 ||
1207         strcmp (scnhdr_int->s_name, ".bss")   == 0)
1208       flags |= IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_WRITE;
1209     else if (strcmp (scnhdr_int->s_name, ".text") == 0)
1210       flags |= IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_EXECUTE;
1211     else if (strcmp (scnhdr_int->s_name, ".reloc") == 0)
1212       flags = (SEC_DATA | IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_DISCARDABLE
1213                | IMAGE_SCN_MEM_SHARED);
1214     else if (strcmp (scnhdr_int->s_name, ".idata") == 0)
1215       flags = IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_WRITE | SEC_DATA;     
1216     else if (strcmp (scnhdr_int->s_name, ".rdata") == 0
1217              || strcmp (scnhdr_int->s_name, ".edata") == 0)
1218       flags =  IMAGE_SCN_MEM_READ | SEC_DATA;     
1219     else if (strcmp (scnhdr_int->s_name, ".pdata") == 0)
1220       flags = IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_ALIGN_4BYTES |
1221                           IMAGE_SCN_MEM_READ ;
1222     /* Remember this field is a max of 8 chars, so the null is _not_ there
1223        for an 8 character name like ".reldata". (yep. Stupid bug) */
1224     else if (strncmp (scnhdr_int->s_name, ".reldata", 8) == 0)
1225       flags =  IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_ALIGN_8BYTES |
1226                IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_WRITE ;
1227     else if (strcmp (scnhdr_int->s_name, ".ydata") == 0)
1228       flags =  IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_ALIGN_8BYTES |
1229                IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_WRITE ;
1230     else if (strncmp (scnhdr_int->s_name, ".drectve", 8) == 0)
1231       flags =  IMAGE_SCN_LNK_INFO | IMAGE_SCN_LNK_REMOVE ;
1232     else if (strncmp (scnhdr_int->s_name, ".stab", 5) == 0)
1233       flags |= (IMAGE_SCN_LNK_INFO | IMAGE_SCN_MEM_DISCARDABLE
1234                 | IMAGE_SCN_MEM_SHARED | IMAGE_SCN_MEM_READ);
1235     else if (strcmp (scnhdr_int->s_name, ".rsrc")  == 0)
1236       flags |= IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_SHARED;
1237     else
1238       flags |= IMAGE_SCN_MEM_READ;
1239
1240     bfd_h_put_32(abfd, flags, (bfd_byte *) scnhdr_ext->s_flags);
1241   }
1242
1243   if (scnhdr_int->s_nlnno <= 0xffff)
1244     bfd_h_put_16(abfd, scnhdr_int->s_nlnno, (bfd_byte *) scnhdr_ext->s_nlnno);
1245   else
1246     {
1247       (*_bfd_error_handler) (_("%s: line number overflow: 0x%lx > 0xffff"),
1248                              bfd_get_filename (abfd),
1249                              scnhdr_int->s_nlnno);
1250       bfd_set_error (bfd_error_file_truncated);
1251       bfd_h_put_16 (abfd, 0xffff, (bfd_byte *) scnhdr_ext->s_nlnno);
1252       ret = 0;
1253     }
1254   if (scnhdr_int->s_nreloc <= 0xffff)
1255     bfd_h_put_16(abfd, scnhdr_int->s_nreloc, (bfd_byte *) scnhdr_ext->s_nreloc);
1256   else
1257     {
1258       (*_bfd_error_handler) (_("%s: reloc overflow: 0x%lx > 0xffff"),
1259                              bfd_get_filename (abfd),
1260                              scnhdr_int->s_nreloc);
1261       bfd_set_error (bfd_error_file_truncated);
1262       bfd_h_put_16 (abfd, 0xffff, (bfd_byte *) scnhdr_ext->s_nreloc);
1263       ret = 0;
1264     }
1265   return ret;
1266 }
1267
1268 static char * dir_names[IMAGE_NUMBEROF_DIRECTORY_ENTRIES] = 
1269 {
1270   N_ ("Export Directory [.edata (or where ever we found it)]"),
1271   N_ ("Import Directory [parts of .idata]"),
1272   N_ ("Resource Directory [.rsrc]"),
1273   N_ ("Exception Directory [.pdata]"),
1274   N_ ("Security Directory"),
1275   N_ ("Base Relocation Directory [.reloc]"),
1276   N_ ("Debug Directory"),
1277   N_ ("Description Directory"),
1278   N_ ("Special Directory"),
1279   N_ ("Thread Storage Directory [.tls]"),
1280   N_ ("Load Configuration Directory"),
1281   N_ ("Bound Import Directory"),
1282   N_ ("Import Address Table Directory"),
1283   N_ ("Reserved"),
1284   N_ ("Reserved"),
1285   N_ ("Reserved")
1286 };
1287
1288 /**********************************************************************/
1289 static boolean
1290 pe_print_idata(abfd, vfile)
1291      bfd *abfd;
1292      PTR vfile;
1293 {
1294   FILE *file = (FILE *) vfile;
1295   bfd_byte *data = 0;
1296   asection *section = bfd_get_section_by_name (abfd, ".idata");
1297   unsigned long adj;
1298
1299 #ifdef POWERPC_LE_PE
1300   asection *rel_section = bfd_get_section_by_name (abfd, ".reldata");
1301 #endif
1302
1303   bfd_size_type datasize;
1304   bfd_size_type dataoff;
1305   bfd_size_type secsize;
1306   bfd_size_type i;
1307   bfd_size_type start, stop;
1308   int onaline = 20;
1309
1310   pe_data_type *pe = pe_data (abfd);
1311   struct internal_extra_pe_aouthdr *extra = &pe->pe_opthdr;
1312
1313   if (section != NULL)
1314     {
1315       datasize = bfd_section_size (abfd, section);
1316       dataoff = 0;
1317
1318       if (datasize == 0)
1319         return true;
1320     }
1321   else
1322     {
1323       bfd_vma addr, size;
1324
1325       addr = extra->DataDirectory[1].VirtualAddress;
1326       size = extra->DataDirectory[1].Size;
1327
1328       if (addr == 0 || size == 0)
1329         return true;
1330
1331       for (section = abfd->sections; section != NULL; section = section->next)
1332         {
1333           if (section->vma - extra->ImageBase <= addr
1334               && ((section->vma - extra->ImageBase
1335                    + bfd_section_size (abfd, section))
1336                   >= addr + size))
1337             break;
1338         }
1339       if (section == NULL)
1340         return true;
1341
1342       /* For some reason the import table size is not reliable.  The
1343          import data will extend past the indicated size, and before
1344          the indicated address.  */
1345       dataoff = addr - (section->vma - extra->ImageBase);
1346       datasize = size;
1347     }
1348
1349 #ifdef POWERPC_LE_PE
1350   if (rel_section != 0 && bfd_section_size (abfd, rel_section) != 0)
1351     {
1352       /* The toc address can be found by taking the starting address,
1353          which on the PPC locates a function descriptor. The descriptor
1354          consists of the function code starting address followed by the
1355          address of the toc. The starting address we get from the bfd,
1356          and the descriptor is supposed to be in the .reldata section. 
1357       */
1358
1359       bfd_vma loadable_toc_address;
1360       bfd_vma toc_address;
1361       bfd_vma start_address;
1362       bfd_byte *data = 0;
1363       int offset;
1364       data = (bfd_byte *) bfd_malloc ((size_t) bfd_section_size (abfd, 
1365                                                                  rel_section));
1366       if (data == NULL && bfd_section_size (abfd, rel_section) != 0)
1367         return false;
1368
1369       datasize = bfd_section_size (abfd, rel_section);
1370   
1371       bfd_get_section_contents (abfd, 
1372                                 rel_section, 
1373                                 (PTR) data, 0, 
1374                                 bfd_section_size (abfd, rel_section));
1375
1376       offset = abfd->start_address - rel_section->vma;
1377
1378       start_address = bfd_get_32(abfd, data+offset);
1379       loadable_toc_address = bfd_get_32(abfd, data+offset+4);
1380       toc_address = loadable_toc_address - 32768;
1381
1382       fprintf(file,
1383               _("\nFunction descriptor located at the start address: %04lx\n"),
1384               (unsigned long int) (abfd->start_address));
1385       fprintf (file,
1386                _("\tcode-base %08lx toc (loadable/actual) %08lx/%08lx\n"), 
1387                start_address, loadable_toc_address, toc_address);
1388     }
1389   else 
1390     {
1391       fprintf(file,
1392               _("\nNo reldata section! Function descriptor not decoded.\n"));
1393     }
1394 #endif
1395
1396   fprintf(file,
1397           _("\nThe Import Tables (interpreted .idata section contents)\n"));
1398   fprintf(file,
1399           _(" vma:            Hint    Time      Forward  DLL       First\n"));
1400   fprintf(file,
1401           _("                 Table   Stamp     Chain    Name      Thunk\n"));
1402
1403   secsize = bfd_section_size (abfd, section);
1404   data = (bfd_byte *) bfd_malloc (secsize);
1405   if (data == NULL && secsize != 0)
1406     return false;
1407
1408   if (! bfd_get_section_contents (abfd, section, (PTR) data, 0, secsize))
1409     return false;
1410
1411   adj = (extra->ImageBase - section->vma) & 0xffffffff;
1412
1413   start = dataoff;
1414   stop = dataoff + datasize;
1415   for (i = start; i < stop; i += onaline)
1416     {
1417       bfd_vma hint_addr;
1418       bfd_vma time_stamp;
1419       bfd_vma forward_chain;
1420       bfd_vma dll_name;
1421       bfd_vma first_thunk;
1422       int idx = 0;
1423       bfd_size_type j;
1424       char *dll;
1425
1426       fprintf (file,
1427                " %08lx\t", 
1428                (unsigned long int) (i + section->vma + dataoff));
1429       
1430       if (i+20 > stop)
1431         {
1432           /* check stuff */
1433           ;
1434         }
1435       
1436       hint_addr = bfd_get_32(abfd, data+i);
1437       time_stamp = bfd_get_32(abfd, data+i+4);
1438       forward_chain = bfd_get_32(abfd, data+i+8);
1439       dll_name = bfd_get_32(abfd, data+i+12);
1440       first_thunk = bfd_get_32(abfd, data+i+16);
1441       
1442       fprintf(file, "%08lx %08lx %08lx %08lx %08lx\n",
1443               hint_addr,
1444               time_stamp,
1445               forward_chain,
1446               dll_name,
1447               first_thunk);
1448
1449       if (hint_addr == 0 && first_thunk == 0)
1450         break;
1451
1452       /* the image base is present in the section->vma */
1453       dll = (char *) data + dll_name + adj;
1454       fprintf(file, _("\n\tDLL Name: %s\n"), dll);
1455
1456       if (hint_addr != 0)
1457         {
1458           fprintf (file, _("\tvma:  Hint/Ord Member-Name\n"));
1459
1460           idx = hint_addr + adj;
1461
1462           for (j = 0; j < stop; j += 4)
1463             {
1464               unsigned long member = bfd_get_32 (abfd, data + idx + j);
1465
1466               if (member == 0)
1467                 break;
1468               if (member & 0x80000000)
1469                 fprintf (file, "\t%04lx\t %4lu", member,
1470                          member & 0x7fffffff);
1471               else
1472                 {
1473                   int ordinal;
1474                   char *member_name;
1475
1476                   ordinal = bfd_get_16 (abfd, data + member + adj);
1477                   member_name = (char *) data + member + adj + 2;
1478                   fprintf (file, "\t%04lx\t %4d  %s",
1479                            member, ordinal, member_name);
1480                 }
1481
1482               /* If the time stamp is not zero, the import address
1483                  table holds actual addresses.  */
1484               if (time_stamp != 0
1485                   && first_thunk != 0
1486                   && first_thunk != hint_addr)
1487                 fprintf (file, "\t%04lx",
1488                          bfd_get_32 (abfd, data + first_thunk + adj + j));
1489
1490               fprintf (file, "\n");
1491             }
1492         }
1493
1494       if (hint_addr != first_thunk && time_stamp == 0)
1495         {
1496           int differ = 0;
1497           int idx2;
1498
1499           idx2 = first_thunk + adj;
1500
1501           for (j=0;j<stop;j+=4)
1502             {
1503               int ordinal;
1504               char *member_name;
1505               bfd_vma hint_member = 0;
1506               bfd_vma iat_member;
1507
1508               if (hint_addr != 0)
1509                 hint_member = bfd_get_32 (abfd, data + idx + j);
1510               iat_member = bfd_get_32 (abfd, data + idx2 + j);
1511
1512               if (hint_addr == 0 && iat_member == 0)
1513                 break;
1514
1515               if (hint_addr == 0 || hint_member != iat_member)
1516                 {
1517                   if (differ == 0)
1518                     {
1519                       fprintf (file, 
1520                                _("\tThe Import Address Table (difference found)\n"));
1521                       fprintf(file, _("\tvma:  Hint/Ord Member-Name\n"));
1522                       differ = 1;
1523                     }
1524                   if (iat_member == 0)
1525                     {
1526                       fprintf(file,
1527                               _("\t>>> Ran out of IAT members!\n"));
1528                     }
1529                   else 
1530                     {
1531                       ordinal = bfd_get_16(abfd,
1532                                            data + iat_member + adj);
1533                       member_name = (char *) data + iat_member + adj + 2;
1534                       fprintf(file, "\t%04lx\t %4d  %s\n",
1535                               iat_member, ordinal, member_name);
1536                     }
1537                 }
1538
1539               if (hint_addr != 0 && hint_member == 0)
1540                 break;
1541             }
1542           if (differ == 0)
1543             {
1544               fprintf(file,
1545                       _("\tThe Import Address Table is identical\n"));
1546             }
1547         }
1548
1549       fprintf(file, "\n");
1550
1551     }
1552
1553   free (data);
1554
1555   return true;
1556 }
1557
1558 static boolean
1559 pe_print_edata (abfd, vfile)
1560      bfd *abfd;
1561      PTR vfile;
1562 {
1563   FILE *file = (FILE *) vfile;
1564   bfd_byte *data = 0;
1565   asection *section = bfd_get_section_by_name (abfd, ".edata");
1566
1567   bfd_size_type datasize;
1568   bfd_size_type dataoff;
1569   bfd_size_type i;
1570
1571   int adj;
1572   struct EDT_type 
1573     {
1574       long export_flags;             /* reserved - should be zero */
1575       long time_stamp;
1576       short major_ver;
1577       short minor_ver;
1578       bfd_vma name;                  /* rva - relative to image base */
1579       long base;                     /* ordinal base */
1580       unsigned long num_functions;   /* Number in the export address table */
1581       unsigned long num_names;       /* Number in the name pointer table */
1582       bfd_vma eat_addr;    /* rva to the export address table */
1583       bfd_vma npt_addr;        /* rva to the Export Name Pointer Table */
1584       bfd_vma ot_addr; /* rva to the Ordinal Table */
1585     } edt;
1586
1587   pe_data_type *pe = pe_data (abfd);
1588   struct internal_extra_pe_aouthdr *extra = &pe->pe_opthdr;
1589
1590   if (section != NULL)
1591     {
1592       datasize = bfd_section_size (abfd, section);
1593       dataoff = 0;
1594     }
1595   else
1596     {
1597       bfd_vma addr, size;
1598
1599       addr = extra->DataDirectory[0].VirtualAddress;
1600       size = extra->DataDirectory[0].Size;
1601
1602       if (addr == 0 || size == 0)
1603         return true;
1604
1605       for (section = abfd->sections; section != NULL; section = section->next)
1606         {
1607           if (section->vma - extra->ImageBase <= addr
1608               && ((section->vma - extra->ImageBase
1609                    + bfd_section_size (abfd, section))
1610                   >= addr + size))
1611             break;
1612         }
1613       if (section == NULL)
1614         return true;
1615
1616       datasize = size;
1617       dataoff = addr - (section->vma - extra->ImageBase);
1618     }
1619
1620   data = (bfd_byte *) bfd_malloc (datasize);
1621   if (data == NULL && datasize != 0)
1622     return false;
1623
1624   if (! bfd_get_section_contents (abfd, section, (PTR) data, dataoff,
1625                                   datasize))
1626     return false;
1627
1628   /* Go get Export Directory Table */
1629   edt.export_flags   = bfd_get_32(abfd, data+0); 
1630   edt.time_stamp     = bfd_get_32(abfd, data+4);
1631   edt.major_ver      = bfd_get_16(abfd, data+8);
1632   edt.minor_ver      = bfd_get_16(abfd, data+10);
1633   edt.name           = bfd_get_32(abfd, data+12);
1634   edt.base           = bfd_get_32(abfd, data+16);
1635   edt.num_functions  = bfd_get_32(abfd, data+20); 
1636   edt.num_names      = bfd_get_32(abfd, data+24); 
1637   edt.eat_addr       = bfd_get_32(abfd, data+28);
1638   edt.npt_addr       = bfd_get_32(abfd, data+32); 
1639   edt.ot_addr        = bfd_get_32(abfd, data+36);
1640
1641   adj = (extra->ImageBase - (section->vma + dataoff)) & 0xffffffff;
1642
1643
1644   /* Dump the EDT first first */
1645   fprintf(file,
1646           _("\nThe Export Tables (interpreted .edata section contents)\n\n"));
1647
1648   fprintf(file,
1649           _("Export Flags \t\t\t%lx\n"), (unsigned long) edt.export_flags);
1650
1651   fprintf(file,
1652           _("Time/Date stamp \t\t%lx\n"), (unsigned long) edt.time_stamp);
1653
1654   fprintf(file,
1655           _("Major/Minor \t\t\t%d/%d\n"), edt.major_ver, edt.minor_ver);
1656
1657   fprintf (file,
1658            _("Name \t\t\t\t"));
1659   fprintf_vma (file, edt.name);
1660   fprintf (file,
1661            " %s\n", data + edt.name + adj);
1662
1663   fprintf(file,
1664           _("Ordinal Base \t\t\t%ld\n"), edt.base);
1665
1666   fprintf(file,
1667           _("Number in:\n"));
1668
1669   fprintf(file,
1670           _("\tExport Address Table \t\t%lx\n"),
1671           edt.num_functions);
1672
1673   fprintf(file,
1674           _("\t[Name Pointer/Ordinal] Table\t%lu\n"), edt.num_names);
1675
1676   fprintf(file,
1677           _("Table Addresses\n"));
1678
1679   fprintf (file,
1680            _("\tExport Address Table \t\t"));
1681   fprintf_vma (file, edt.eat_addr);
1682   fprintf (file, "\n");
1683
1684   fprintf (file,
1685           _("\tName Pointer Table \t\t"));
1686   fprintf_vma (file, edt.npt_addr);
1687   fprintf (file, "\n");
1688
1689   fprintf (file,
1690            _("\tOrdinal Table \t\t\t"));
1691   fprintf_vma (file, edt.ot_addr);
1692   fprintf (file, "\n");
1693
1694   
1695   /* The next table to find si the Export Address Table. It's basically
1696      a list of pointers that either locate a function in this dll, or
1697      forward the call to another dll. Something like:
1698       typedef union 
1699       {
1700         long export_rva;
1701         long forwarder_rva;
1702       } export_address_table_entry;
1703   */
1704
1705   fprintf(file,
1706           _("\nExport Address Table -- Ordinal Base %ld\n"),
1707           edt.base);
1708
1709   for (i = 0; i < edt.num_functions; ++i)
1710     {
1711       bfd_vma eat_member = bfd_get_32 (abfd, 
1712                                        data + edt.eat_addr + (i * 4) + adj);
1713       bfd_vma eat_actual = (extra->ImageBase + eat_member) & 0xffffffff;
1714       bfd_vma edata_start = bfd_get_section_vma (abfd,section) + dataoff;
1715       bfd_vma edata_end = edata_start + datasize;
1716
1717       if (eat_member == 0)
1718         continue;
1719
1720       if (edata_start < eat_actual && eat_actual < edata_end) 
1721         {
1722           /* this rva is to a name (forwarding function) in our section */
1723           /* Should locate a function descriptor */
1724           fprintf(file,
1725                   "\t[%4ld] +base[%4ld] %04lx %s -- %s\n", 
1726                   (long) i, (long) (i + edt.base), eat_member,
1727                   "Forwarder RVA", data + eat_member + adj);
1728         }
1729       else
1730         {
1731           /* Should locate a function descriptor in the reldata section */
1732           fprintf(file,
1733                   "\t[%4ld] +base[%4ld] %04lx %s\n", 
1734                   (long) i, (long) (i + edt.base), eat_member, "Export RVA");
1735         }
1736     }
1737
1738   /* The Export Name Pointer Table is paired with the Export Ordinal Table */
1739   /* Dump them in parallel for clarity */
1740   fprintf(file,
1741           _("\n[Ordinal/Name Pointer] Table\n"));
1742
1743   for (i = 0; i < edt.num_names; ++i)
1744     {
1745       bfd_vma name_ptr = bfd_get_32(abfd, 
1746                                     data + 
1747                                     edt.npt_addr
1748                                     + (i*4) + adj);
1749       
1750       char *name = (char *) data + name_ptr + adj;
1751
1752       bfd_vma ord = bfd_get_16(abfd, 
1753                                     data + 
1754                                     edt.ot_addr
1755                                     + (i*2) + adj);
1756       fprintf(file,
1757               "\t[%4ld] %s\n", (long) ord, name);
1758
1759     }
1760
1761   free (data);
1762
1763   return true;
1764 }
1765
1766 static boolean
1767 pe_print_pdata (abfd, vfile)
1768      bfd  *abfd;
1769      PTR vfile;
1770 {
1771   FILE *file = (FILE *) vfile;
1772   bfd_byte *data = 0;
1773   asection *section = bfd_get_section_by_name (abfd, ".pdata");
1774   bfd_size_type datasize = 0;
1775   bfd_size_type i;
1776   bfd_size_type start, stop;
1777   int onaline = 20;
1778
1779   if (section == 0)
1780     return true;
1781
1782   stop = bfd_section_size (abfd, section);
1783   if ((stop % onaline) != 0)
1784     fprintf (file, _("Warning, .pdata section size (%ld) is not a multiple of %d\n"),
1785              (long)stop, onaline);
1786
1787   fprintf(file,
1788           _("\nThe Function Table (interpreted .pdata section contents)\n"));
1789   fprintf(file,
1790           _(" vma:\t\tBegin    End      EH       EH       PrologEnd\n"));
1791   fprintf(file,
1792           _("     \t\tAddress  Address  Handler  Data     Address\n"));
1793
1794   if (bfd_section_size (abfd, section) == 0)
1795     return true;
1796
1797   data = (bfd_byte *) bfd_malloc ((size_t) bfd_section_size (abfd, section));
1798   datasize = bfd_section_size (abfd, section);
1799   if (data == NULL && datasize != 0)
1800     return false;
1801
1802   bfd_get_section_contents (abfd, 
1803                             section, 
1804                             (PTR) data, 0, 
1805                             bfd_section_size (abfd, section));
1806
1807   start = 0;
1808
1809   for (i = start; i < stop; i += onaline)
1810     {
1811       bfd_vma begin_addr;
1812       bfd_vma end_addr;
1813       bfd_vma eh_handler;
1814       bfd_vma eh_data;
1815       bfd_vma prolog_end_addr;
1816
1817       if (i+20 > stop)
1818           break;
1819       
1820       begin_addr = bfd_get_32(abfd, data+i);
1821       end_addr = bfd_get_32(abfd, data+i+4);
1822       eh_handler = bfd_get_32(abfd, data+i+8);
1823       eh_data = bfd_get_32(abfd, data+i+12);
1824       prolog_end_addr = bfd_get_32(abfd, data+i+16);
1825       
1826       if (begin_addr == 0 && end_addr == 0 && eh_handler == 0
1827           && eh_data == 0 && prolog_end_addr == 0)
1828         {
1829           /* We are probably into the padding of the
1830              section now */
1831           break;
1832         }
1833
1834       fprintf (file,
1835                " %08lx\t", 
1836                (unsigned long int) (i + section->vma));
1837
1838       fprintf(file, "%08lx %08lx %08lx %08lx %08lx",
1839               begin_addr,
1840               end_addr,
1841               eh_handler,
1842               eh_data,
1843               prolog_end_addr);
1844
1845 #ifdef POWERPC_LE_PE
1846       if (eh_handler == 0 && eh_data != 0)
1847         {
1848           /* Special bits here, although the meaning may */
1849           /* be a little mysterious. The only one I know */
1850           /* for sure is 0x03.                           */
1851           /* Code Significance                           */
1852           /* 0x00 None                                   */
1853           /* 0x01 Register Save Millicode                */
1854           /* 0x02 Register Restore Millicode             */
1855           /* 0x03 Glue Code Sequence                     */
1856           switch (eh_data)
1857             {
1858             case 0x01:
1859               fprintf(file, _(" Register save millicode"));
1860               break;
1861             case 0x02:
1862               fprintf(file, _(" Register restore millicode"));
1863               break;
1864             case 0x03:
1865               fprintf(file, _(" Glue code sequence"));
1866               break;
1867             default:
1868               break;
1869             }
1870         }
1871 #endif     
1872       fprintf(file, "\n");
1873     }
1874
1875   free (data);
1876
1877   return true;
1878 }
1879
1880 static const char *tbl[6] =
1881 {
1882 "ABSOLUTE",
1883 "HIGH",
1884 "LOW",
1885 "HIGHLOW",
1886 "HIGHADJ",
1887 "MIPS_JMPADDR"
1888 };
1889
1890 static boolean
1891 pe_print_reloc (abfd, vfile)
1892      bfd *abfd;
1893      PTR vfile;
1894 {
1895   FILE *file = (FILE *) vfile;
1896   bfd_byte *data = 0;
1897   asection *section = bfd_get_section_by_name (abfd, ".reloc");
1898   bfd_size_type datasize = 0;
1899   bfd_size_type i;
1900   bfd_size_type start, stop;
1901
1902   if (section == 0)
1903     return true;
1904
1905   if (bfd_section_size (abfd, section) == 0)
1906     return true;
1907
1908   fprintf(file,
1909           _("\n\nPE File Base Relocations (interpreted .reloc section contents)\n"));
1910
1911   data = (bfd_byte *) bfd_malloc ((size_t) bfd_section_size (abfd, section));
1912   datasize = bfd_section_size (abfd, section);
1913   if (data == NULL && datasize != 0)
1914     return false;
1915
1916   bfd_get_section_contents (abfd, 
1917                             section, 
1918                             (PTR) data, 0, 
1919                             bfd_section_size (abfd, section));
1920
1921   start = 0;
1922
1923   stop = bfd_section_size (abfd, section);
1924
1925   for (i = start; i < stop;)
1926     {
1927       int j;
1928       bfd_vma virtual_address;
1929       long number, size;
1930
1931       /* The .reloc section is a sequence of blocks, with a header consisting
1932          of two 32 bit quantities, followed by a number of 16 bit entries */
1933
1934       virtual_address = bfd_get_32(abfd, data+i);
1935       size = bfd_get_32(abfd, data+i+4);
1936       number = (size - 8) / 2;
1937
1938       if (size == 0) 
1939         {
1940           break;
1941         }
1942
1943       fprintf (file,
1944                _("\nVirtual Address: %08lx Chunk size %ld (0x%lx) Number of fixups %ld\n"),
1945                virtual_address, size, size, number);
1946
1947       for (j = 0; j < number; ++j)
1948         {
1949           unsigned short e = bfd_get_16(abfd, data + i + 8 + j*2);
1950           int t =   (e & 0xF000) >> 12;
1951           int off = e & 0x0FFF;
1952
1953           if (t > 5) 
1954             abort();
1955
1956           fprintf(file,
1957                   _("\treloc %4d offset %4x [%4lx] %s\n"), 
1958                   j, off, (long) (off + virtual_address), tbl[t]);
1959           
1960         }
1961       i += size;
1962     }
1963
1964   free (data);
1965
1966   return true;
1967 }
1968
1969 static boolean
1970 pe_print_private_bfd_data (abfd, vfile)
1971      bfd *abfd;
1972      PTR vfile;
1973 {
1974   FILE *file = (FILE *) vfile;
1975   int j;
1976   pe_data_type *pe = pe_data (abfd);
1977   struct internal_extra_pe_aouthdr *i = &pe->pe_opthdr;
1978
1979   /* The MS dumpbin program reportedly ands with 0xff0f before
1980      printing the characteristics field.  Not sure why.  No reason to
1981      emulate it here.  */
1982   fprintf (file, _("\nCharacteristics 0x%x\n"), pe->real_flags);
1983 #undef PF
1984 #define PF(x, y)    if (pe->real_flags & x) { fprintf (file, "\t%s\n", y); }
1985   PF (F_RELFLG, "relocations stripped");
1986   PF (F_EXEC, "executable");
1987   PF (F_LNNO, "line numbers stripped");
1988   PF (F_LSYMS, "symbols stripped");
1989   PF (0x80, "little endian");
1990   PF (F_AR32WR, "32 bit words");
1991   PF (0x200, "debugging information removed");
1992   PF (0x1000, "system file");
1993   PF (F_DLL, "DLL");
1994   PF (0x8000, "big endian");
1995 #undef PF
1996
1997   fprintf (file,"\nImageBase\t\t");
1998   fprintf_vma (file, i->ImageBase);
1999   fprintf (file,"\nSectionAlignment\t");
2000   fprintf_vma (file, i->SectionAlignment);
2001   fprintf (file,"\nFileAlignment\t\t");
2002   fprintf_vma (file, i->FileAlignment);
2003   fprintf (file,"\nMajorOSystemVersion\t%d\n", i->MajorOperatingSystemVersion);
2004   fprintf (file,"MinorOSystemVersion\t%d\n", i->MinorOperatingSystemVersion);
2005   fprintf (file,"MajorImageVersion\t%d\n", i->MajorImageVersion);
2006   fprintf (file,"MinorImageVersion\t%d\n", i->MinorImageVersion);
2007   fprintf (file,"MajorSubsystemVersion\t%d\n", i->MajorSubsystemVersion);
2008   fprintf (file,"MinorSubsystemVersion\t%d\n", i->MinorSubsystemVersion);
2009   fprintf (file,"Reserved1\t\t%08lx\n", i->Reserved1);
2010   fprintf (file,"SizeOfImage\t\t%08lx\n", i->SizeOfImage);
2011   fprintf (file,"SizeOfHeaders\t\t%08lx\n", i->SizeOfHeaders);
2012   fprintf (file,"CheckSum\t\t%08lx\n", i->CheckSum);
2013   fprintf (file,"Subsystem\t\t%08x\n", i->Subsystem);
2014   fprintf (file,"DllCharacteristics\t%08x\n", i->DllCharacteristics);
2015   fprintf (file,"SizeOfStackReserve\t");
2016   fprintf_vma (file, i->SizeOfStackReserve);
2017   fprintf (file,"\nSizeOfStackCommit\t");
2018   fprintf_vma (file, i->SizeOfStackCommit);
2019   fprintf (file,"\nSizeOfHeapReserve\t");
2020   fprintf_vma (file, i->SizeOfHeapReserve);
2021   fprintf (file,"\nSizeOfHeapCommit\t");
2022   fprintf_vma (file, i->SizeOfHeapCommit);
2023   fprintf (file,"\nLoaderFlags\t\t%08lx\n", i->LoaderFlags);
2024   fprintf (file,"NumberOfRvaAndSizes\t%08lx\n", i->NumberOfRvaAndSizes);
2025
2026   fprintf (file,"\nThe Data Directory\n");
2027   for (j = 0; j < IMAGE_NUMBEROF_DIRECTORY_ENTRIES; j++) 
2028     {
2029       fprintf (file, "Entry %1x ", j);
2030       fprintf_vma (file, i->DataDirectory[j].VirtualAddress);
2031       fprintf (file, " %08lx ", i->DataDirectory[j].Size);
2032       fprintf (file, "%s\n", dir_names[j]);
2033     }
2034
2035   pe_print_idata (abfd, vfile);
2036   pe_print_edata (abfd, vfile);
2037   pe_print_pdata (abfd, vfile);
2038   pe_print_reloc (abfd, vfile);
2039
2040   if (pe_saved_coff_bfd_print_private_bfd_data != NULL)
2041     {
2042       fputc ('\n', file);
2043   
2044       return pe_saved_coff_bfd_print_private_bfd_data (abfd, vfile);
2045     }
2046
2047   return true;
2048 }
2049
2050 static boolean
2051 pe_mkobject (abfd)
2052      bfd * abfd;
2053 {
2054   pe_data_type *pe;
2055   abfd->tdata.pe_obj_data = 
2056     (struct pe_tdata *) bfd_zalloc (abfd, sizeof (pe_data_type));
2057
2058   if (abfd->tdata.pe_obj_data == 0)
2059     return false;
2060
2061   pe = pe_data (abfd);
2062
2063   pe->coff.pe = 1;
2064   pe->in_reloc_p = in_reloc_p;
2065   return true;
2066 }
2067
2068 /* Create the COFF backend specific information.  */
2069 static PTR
2070 pe_mkobject_hook (abfd, filehdr, aouthdr)
2071      bfd * abfd;
2072      PTR filehdr;
2073      PTR aouthdr;
2074 {
2075   struct internal_filehdr *internal_f = (struct internal_filehdr *) filehdr;
2076   pe_data_type *pe;
2077
2078   if (pe_mkobject (abfd) == false)
2079     return NULL;
2080
2081   pe = pe_data (abfd);
2082   pe->coff.sym_filepos = internal_f->f_symptr;
2083   /* These members communicate important constants about the symbol
2084      table to GDB's symbol-reading code.  These `constants'
2085      unfortunately vary among coff implementations...  */
2086   pe->coff.local_n_btmask = N_BTMASK;
2087   pe->coff.local_n_btshft = N_BTSHFT;
2088   pe->coff.local_n_tmask = N_TMASK;
2089   pe->coff.local_n_tshift = N_TSHIFT;
2090   pe->coff.local_symesz = SYMESZ;
2091   pe->coff.local_auxesz = AUXESZ;
2092   pe->coff.local_linesz = LINESZ;
2093
2094   obj_raw_syment_count (abfd) =
2095     obj_conv_table_size (abfd) =
2096       internal_f->f_nsyms;
2097
2098   pe->real_flags = internal_f->f_flags;
2099
2100   if ((internal_f->f_flags & F_DLL) != 0)
2101     pe->dll = 1;
2102
2103 #ifdef COFF_IMAGE_WITH_PE
2104   if (aouthdr) 
2105     pe->pe_opthdr = ((struct internal_aouthdr *)aouthdr)->pe;
2106 #endif
2107
2108 #ifdef ARM 
2109   if (! _bfd_coff_arm_set_private_flags (abfd, internal_f->f_flags))
2110     coff_data (abfd) ->flags = 0;
2111 #endif
2112   
2113   return (PTR) pe;
2114 }
2115
2116
2117
2118 /* Copy any private info we understand from the input bfd
2119    to the output bfd.  */
2120
2121 #ifdef coff_bfd_copy_private_bfd_data
2122 static boolean (*pe_saved_coff_bfd_copy_private_bfd_data)
2123      PARAMS ((bfd *, bfd *))
2124      = coff_bfd_copy_private_bfd_data;
2125 #undef coff_bfd_copy_private_bfd_data
2126 #else
2127 static boolean (*pe_saved_coff_bfd_copy_private_bfd_data)
2128      PARAMS ((bfd *, bfd *))
2129      = NULL;
2130 #endif
2131 #define coff_bfd_copy_private_bfd_data pe_bfd_copy_private_bfd_data
2132
2133 static boolean
2134 pe_bfd_copy_private_bfd_data (ibfd, obfd)
2135      bfd *ibfd, *obfd;
2136 {
2137   /* One day we may try to grok other private data.  */
2138   if (ibfd->xvec->flavour != bfd_target_coff_flavour
2139       || obfd->xvec->flavour != bfd_target_coff_flavour)
2140     return true;
2141
2142   pe_data (obfd)->pe_opthdr = pe_data (ibfd)->pe_opthdr;
2143   pe_data (obfd)->dll = pe_data (ibfd)->dll;
2144
2145   if (pe_saved_coff_bfd_copy_private_bfd_data)
2146     return pe_saved_coff_bfd_copy_private_bfd_data (ibfd, obfd);
2147   
2148   return true;
2149 }
2150
2151 #ifdef COFF_IMAGE_WITH_PE
2152
2153 /* Copy private section data.  */
2154
2155 #define coff_bfd_copy_private_section_data pe_bfd_copy_private_section_data
2156
2157 static boolean pe_bfd_copy_private_section_data
2158   PARAMS ((bfd *, asection *, bfd *, asection *));
2159
2160 static boolean
2161 pe_bfd_copy_private_section_data (ibfd, isec, obfd, osec)
2162      bfd *ibfd;
2163      asection *isec;
2164      bfd *obfd;
2165      asection *osec;
2166 {
2167   if (bfd_get_flavour (ibfd) != bfd_target_coff_flavour
2168       || bfd_get_flavour (obfd) != bfd_target_coff_flavour)
2169     return true;
2170
2171   if (coff_section_data (ibfd, isec) != NULL
2172       && pei_section_data (ibfd, isec) != NULL)
2173     {
2174       if (coff_section_data (obfd, osec) == NULL)
2175         {
2176           osec->used_by_bfd =
2177             (PTR) bfd_zalloc (obfd, sizeof (struct coff_section_tdata));
2178           if (osec->used_by_bfd == NULL)
2179             return false;
2180         }
2181       if (pei_section_data (obfd, osec) == NULL)
2182         {
2183           coff_section_data (obfd, osec)->tdata =
2184             (PTR) bfd_zalloc (obfd, sizeof (struct pei_section_tdata));
2185           if (coff_section_data (obfd, osec)->tdata == NULL)
2186             return false;
2187         }
2188       pei_section_data (obfd, osec)->virt_size =
2189         pei_section_data (ibfd, isec)->virt_size;
2190     }
2191
2192   return true;
2193 }
2194
2195 #endif