Improve the formatting of the title strings of the binutils manual pages.
[deliverable/binutils-gdb.git] / bfd / peXXigen.c
CommitLineData
277d1b5e 1/* Support for the generic parts of PE/PEI; the common executable parts.
82704155 2 Copyright (C) 1995-2019 Free Software Foundation, Inc.
277d1b5e
ILT
3 Written by Cygnus Solutions.
4
5e226794 5 This file is part of BFD, the Binary File Descriptor library.
277d1b5e 6
5e226794
NC
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
cd123cb7 9 the Free Software Foundation; either version 3 of the License, or
5e226794 10 (at your option) any later version.
277d1b5e 11
5e226794
NC
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.
277d1b5e 16
5e226794
NC
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
cd123cb7
NC
19 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
20 MA 02110-1301, USA. */
21
277d1b5e 22
6fa957a9 23/* Most of this hacked by Steve Chamberlain <sac@cygnus.com>.
277d1b5e 24
6fa957a9 25 PE/PEI rearrangement (and code added): Donn Terry
ca09e32b 26 Softway Systems, Inc. */
277d1b5e
ILT
27
28/* Hey look, some documentation [and in a place you expect to find it]!
29
30 The main reference for the pei format is "Microsoft Portable Executable
31 and Common Object File Format Specification 4.1". Get it if you need to
32 do some serious hacking on this code.
33
34 Another reference:
35 "Peering Inside the PE: A Tour of the Win32 Portable Executable
36 File Format", MSJ 1994, Volume 9.
37
1dd1bc4d
OM
38 The PE/PEI format is also used by .NET. ECMA-335 describes this:
39
40 "Standard ECMA-335 Common Language Infrastructure (CLI)", 6th Edition, June 2012.
41
42 This is also available at
43 https://www.ecma-international.org/publications/files/ECMA-ST/ECMA-335.pdf.
44
277d1b5e
ILT
45 The *sole* difference between the pe format and the pei format is that the
46 latter has an MSDOS 2.0 .exe header on the front that prints the message
47 "This app must be run under Windows." (or some such).
48 (FIXME: Whether that statement is *really* true or not is unknown.
49 Are there more subtle differences between pe and pei formats?
50 For now assume there aren't. If you find one, then for God sakes
51 document it here!)
52
53 The Microsoft docs use the word "image" instead of "executable" because
54 the former can also refer to a DLL (shared library). Confusion can arise
55 because the `i' in `pei' also refers to "image". The `pe' format can
56 also create images (i.e. executables), it's just that to run on a win32
57 system you need to use the pei format.
58
59 FIXME: Please add more docs here so the next poor fool that has to hack
60 on this code has a chance of getting something accomplished without
ca09e32b 61 wasting too much time. */
277d1b5e 62
99ad8390
NC
63/* This expands into COFF_WITH_pe, COFF_WITH_pep, or COFF_WITH_pex64
64 depending on whether we're compiling for straight PE or PE+. */
cbff5e0d
DD
65#define COFF_WITH_XX
66
277d1b5e 67#include "sysdep.h"
3db64b00 68#include "bfd.h"
277d1b5e
ILT
69#include "libbfd.h"
70#include "coff/internal.h"
5fdcb63c 71#include "bfdver.h"
7769fa97 72#include "libiberty.h"
5879bb8f
NC
73#ifdef HAVE_WCHAR_H
74#include <wchar.h>
75#endif
31593e1b
NC
76#ifdef HAVE_WCTYPE_H
77#include <wctype.h>
78#endif
277d1b5e
ILT
79
80/* NOTE: it's strange to be including an architecture specific header
81 in what's supposed to be general (to PE/PEI) code. However, that's
82 where the definitions are, and they don't vary per architecture
83 within PE/PEI, so we get them from there. FIXME: The lack of
84 variance is an assumption which may prove to be incorrect if new
85 PE/PEI targets are created. */
99ad8390
NC
86#if defined COFF_WITH_pex64
87# include "coff/x86_64.h"
88#elif defined COFF_WITH_pep
cbff5e0d
DD
89# include "coff/ia64.h"
90#else
91# include "coff/i386.h"
92#endif
277d1b5e
ILT
93
94#include "coff/pe.h"
95#include "libcoff.h"
96#include "libpei.h"
5879bb8f 97#include "safe-ctype.h"
277d1b5e 98
99ad8390 99#if defined COFF_WITH_pep || defined COFF_WITH_pex64
cbff5e0d
DD
100# undef AOUTSZ
101# define AOUTSZ PEPAOUTSZ
102# define PEAOUTHDR PEPAOUTHDR
103#endif
104
5879bb8f
NC
105#define HighBitSet(val) ((val) & 0x80000000)
106#define SetHighBit(val) ((val) | 0x80000000)
107#define WithoutHighBit(val) ((val) & 0x7fffffff)
108
277d1b5e
ILT
109/* FIXME: This file has various tests of POWERPC_LE_PE. Those tests
110 worked when the code was in peicode.h, but no longer work now that
111 the code is in peigen.c. PowerPC NT is said to be dead. If
112 anybody wants to revive the code, you will have to figure out how
113 to handle those issues. */
1725a96e 114\f
277d1b5e 115void
7920ce38 116_bfd_XXi_swap_sym_in (bfd * abfd, void * ext1, void * in1)
277d1b5e 117{
6fa957a9
KH
118 SYMENT *ext = (SYMENT *) ext1;
119 struct internal_syment *in = (struct internal_syment *) in1;
277d1b5e 120
6fa957a9
KH
121 if (ext->e.e_name[0] == 0)
122 {
123 in->_n._n_n._n_zeroes = 0;
dc810e39 124 in->_n._n_n._n_offset = H_GET_32 (abfd, ext->e.e.e_offset);
6fa957a9
KH
125 }
126 else
1725a96e 127 memcpy (in->_n._n_name, ext->e.e_name, SYMNMLEN);
277d1b5e 128
dc810e39 129 in->n_value = H_GET_32 (abfd, ext->e_value);
9ae678af 130 in->n_scnum = (short) H_GET_16 (abfd, ext->e_scnum);
1725a96e 131
6fa957a9 132 if (sizeof (ext->e_type) == 2)
dc810e39 133 in->n_type = H_GET_16 (abfd, ext->e_type);
6fa957a9 134 else
dc810e39 135 in->n_type = H_GET_32 (abfd, ext->e_type);
1725a96e 136
dc810e39
AM
137 in->n_sclass = H_GET_8 (abfd, ext->e_sclass);
138 in->n_numaux = H_GET_8 (abfd, ext->e_numaux);
277d1b5e
ILT
139
140#ifndef STRICT_PE_FORMAT
6fa957a9 141 /* This is for Gnu-created DLLs. */
277d1b5e
ILT
142
143 /* The section symbols for the .idata$ sections have class 0x68
144 (C_SECTION), which MS documentation indicates is a section
145 symbol. Unfortunately, the value field in the symbol is simply a
146 copy of the .idata section's flags rather than something useful.
147 When these symbols are encountered, change the value to 0 so that
148 they will be handled somewhat correctly in the bfd code. */
149 if (in->n_sclass == C_SECTION)
150 {
383c383f 151 char namebuf[SYMNMLEN + 1];
ba775898 152 const char *name = NULL;
383c383f 153
277d1b5e
ILT
154 in->n_value = 0x0;
155
277d1b5e
ILT
156 /* Create synthetic empty sections as needed. DJ */
157 if (in->n_scnum == 0)
158 {
159 asection *sec;
1725a96e 160
383c383f
AM
161 name = _bfd_coff_internal_syment_name (abfd, in, namebuf);
162 if (name == NULL)
201159ec 163 {
871b3ab2 164 _bfd_error_handler (_("%pB: unable to find name for empty section"),
201159ec
NC
165 abfd);
166 bfd_set_error (bfd_error_invalid_target);
167 return;
168 }
169
383c383f
AM
170 sec = bfd_get_section_by_name (abfd, name);
171 if (sec != NULL)
172 in->n_scnum = sec->target_index;
277d1b5e 173 }
1725a96e 174
277d1b5e
ILT
175 if (in->n_scnum == 0)
176 {
177 int unused_section_number = 0;
178 asection *sec;
117ed4f8 179 flagword flags;
1725a96e 180
6fa957a9 181 for (sec = abfd->sections; sec; sec = sec->next)
277d1b5e 182 if (unused_section_number <= sec->target_index)
6fa957a9 183 unused_section_number = sec->target_index + 1;
277d1b5e 184
383c383f
AM
185 if (name == namebuf)
186 {
a50b1753 187 name = (const char *) bfd_alloc (abfd, strlen (namebuf) + 1);
383c383f 188 if (name == NULL)
201159ec 189 {
871b3ab2 190 _bfd_error_handler (_("%pB: out of memory creating name for empty section"),
201159ec
NC
191 abfd);
192 return;
193 }
383c383f
AM
194 strcpy ((char *) name, namebuf);
195 }
201159ec 196
117ed4f8
AM
197 flags = SEC_HAS_CONTENTS | SEC_ALLOC | SEC_DATA | SEC_LOAD;
198 sec = bfd_make_section_anyway_with_flags (abfd, name, flags);
383c383f 199 if (sec == NULL)
201159ec 200 {
871b3ab2 201 _bfd_error_handler (_("%pB: unable to create fake empty section"),
201159ec
NC
202 abfd);
203 return;
204 }
277d1b5e
ILT
205
206 sec->vma = 0;
207 sec->lma = 0;
eea6121a 208 sec->size = 0;
277d1b5e
ILT
209 sec->filepos = 0;
210 sec->rel_filepos = 0;
211 sec->reloc_count = 0;
212 sec->line_filepos = 0;
213 sec->lineno_count = 0;
214 sec->userdata = NULL;
7920ce38 215 sec->next = NULL;
277d1b5e 216 sec->alignment_power = 2;
277d1b5e
ILT
217
218 sec->target_index = unused_section_number;
219
220 in->n_scnum = unused_section_number;
221 }
222 in->n_sclass = C_STAT;
277d1b5e
ILT
223 }
224#endif
225
226#ifdef coff_swap_sym_in_hook
227 /* This won't work in peigen.c, but since it's for PPC PE, it's not
9602af51 228 worth fixing. */
6fa957a9 229 coff_swap_sym_in_hook (abfd, ext1, in1);
277d1b5e
ILT
230#endif
231}
232
32ae0d80
NC
233static bfd_boolean
234abs_finder (bfd * abfd ATTRIBUTE_UNUSED, asection * sec, void * data)
235{
236 bfd_vma abs_val = * (bfd_vma *) data;
237
3714081c 238 return (sec->vma <= abs_val) && ((sec->vma + (1ULL << 32)) > abs_val);
32ae0d80
NC
239}
240
277d1b5e 241unsigned int
7920ce38 242_bfd_XXi_swap_sym_out (bfd * abfd, void * inp, void * extp)
277d1b5e 243{
6fa957a9
KH
244 struct internal_syment *in = (struct internal_syment *) inp;
245 SYMENT *ext = (SYMENT *) extp;
1725a96e 246
6fa957a9
KH
247 if (in->_n._n_name[0] == 0)
248 {
dc810e39
AM
249 H_PUT_32 (abfd, 0, ext->e.e.e_zeroes);
250 H_PUT_32 (abfd, in->_n._n_n._n_offset, ext->e.e.e_offset);
6fa957a9
KH
251 }
252 else
1725a96e 253 memcpy (ext->e.e_name, in->_n._n_name, SYMNMLEN);
277d1b5e 254
32ae0d80
NC
255 /* The PE32 and PE32+ formats only use 4 bytes to hold the value of a
256 symbol. This is a problem on 64-bit targets where we can generate
257 absolute symbols with values >= 1^32. We try to work around this
258 problem by finding a section whose base address is sufficient to
259 reduce the absolute value to < 1^32, and then transforming the
260 symbol into a section relative symbol. This of course is a hack. */
261 if (sizeof (in->n_value) > 4
40af4a36
NC
262 /* The strange computation of the shift amount is here in order to
263 avoid a compile time warning about the comparison always being
264 false. It does not matter if this test fails to work as expected
265 as the worst that can happen is that some absolute symbols are
266 needlessly converted into section relative symbols. */
267 && in->n_value > ((1ULL << (sizeof (in->n_value) > 4 ? 32 : 31)) - 1)
9ae678af 268 && in->n_scnum == N_ABS)
32ae0d80
NC
269 {
270 asection * sec;
271
272 sec = bfd_sections_find_if (abfd, abs_finder, & in->n_value);
273 if (sec)
274 {
275 in->n_value -= sec->vma;
276 in->n_scnum = sec->target_index;
277 }
278 /* else: FIXME: The value is outside the range of any section. This
88667baf 279 happens for __image_base__ and __ImageBase and maybe some other
32ae0d80
NC
280 symbols as well. We should find a way to handle these values. */
281 }
282
dc810e39
AM
283 H_PUT_32 (abfd, in->n_value, ext->e_value);
284 H_PUT_16 (abfd, in->n_scnum, ext->e_scnum);
1725a96e 285
9602af51 286 if (sizeof (ext->e_type) == 2)
dc810e39 287 H_PUT_16 (abfd, in->n_type, ext->e_type);
277d1b5e 288 else
dc810e39 289 H_PUT_32 (abfd, in->n_type, ext->e_type);
1725a96e 290
dc810e39
AM
291 H_PUT_8 (abfd, in->n_sclass, ext->e_sclass);
292 H_PUT_8 (abfd, in->n_numaux, ext->e_numaux);
277d1b5e
ILT
293
294 return SYMESZ;
295}
296
297void
7920ce38
NC
298_bfd_XXi_swap_aux_in (bfd * abfd,
299 void * ext1,
300 int type,
96d56e9f 301 int in_class,
7920ce38
NC
302 int indx ATTRIBUTE_UNUSED,
303 int numaux ATTRIBUTE_UNUSED,
07d6d2b8 304 void * in1)
277d1b5e 305{
6fa957a9
KH
306 AUXENT *ext = (AUXENT *) ext1;
307 union internal_auxent *in = (union internal_auxent *) in1;
308
201159ec
NC
309 /* PR 17521: Make sure that all fields in the aux structure
310 are initialised. */
311 memset (in, 0, sizeof * in);
96d56e9f 312 switch (in_class)
6fa957a9
KH
313 {
314 case C_FILE:
315 if (ext->x_file.x_fname[0] == 0)
316 {
317 in->x_file.x_n.x_zeroes = 0;
dc810e39 318 in->x_file.x_n.x_offset = H_GET_32 (abfd, ext->x_file.x_n.x_offset);
6fa957a9
KH
319 }
320 else
1725a96e 321 memcpy (in->x_file.x_fname, ext->x_file.x_fname, FILNMLEN);
277d1b5e 322 return;
6fa957a9
KH
323
324 case C_STAT:
325 case C_LEAFSTAT:
326 case C_HIDDEN:
327 if (type == T_NULL)
328 {
329 in->x_scn.x_scnlen = GET_SCN_SCNLEN (abfd, ext);
330 in->x_scn.x_nreloc = GET_SCN_NRELOC (abfd, ext);
331 in->x_scn.x_nlinno = GET_SCN_NLINNO (abfd, ext);
dc810e39
AM
332 in->x_scn.x_checksum = H_GET_32 (abfd, ext->x_scn.x_checksum);
333 in->x_scn.x_associated = H_GET_16 (abfd, ext->x_scn.x_associated);
334 in->x_scn.x_comdat = H_GET_8 (abfd, ext->x_scn.x_comdat);
6fa957a9
KH
335 return;
336 }
337 break;
277d1b5e 338 }
277d1b5e 339
dc810e39
AM
340 in->x_sym.x_tagndx.l = H_GET_32 (abfd, ext->x_sym.x_tagndx);
341 in->x_sym.x_tvndx = H_GET_16 (abfd, ext->x_sym.x_tvndx);
277d1b5e 342
96d56e9f
NC
343 if (in_class == C_BLOCK || in_class == C_FCN || ISFCN (type)
344 || ISTAG (in_class))
277d1b5e
ILT
345 {
346 in->x_sym.x_fcnary.x_fcn.x_lnnoptr = GET_FCN_LNNOPTR (abfd, ext);
347 in->x_sym.x_fcnary.x_fcn.x_endndx.l = GET_FCN_ENDNDX (abfd, ext);
348 }
349 else
350 {
351 in->x_sym.x_fcnary.x_ary.x_dimen[0] =
dc810e39 352 H_GET_16 (abfd, ext->x_sym.x_fcnary.x_ary.x_dimen[0]);
277d1b5e 353 in->x_sym.x_fcnary.x_ary.x_dimen[1] =
dc810e39 354 H_GET_16 (abfd, ext->x_sym.x_fcnary.x_ary.x_dimen[1]);
277d1b5e 355 in->x_sym.x_fcnary.x_ary.x_dimen[2] =
dc810e39 356 H_GET_16 (abfd, ext->x_sym.x_fcnary.x_ary.x_dimen[2]);
277d1b5e 357 in->x_sym.x_fcnary.x_ary.x_dimen[3] =
dc810e39 358 H_GET_16 (abfd, ext->x_sym.x_fcnary.x_ary.x_dimen[3]);
277d1b5e
ILT
359 }
360
6fa957a9
KH
361 if (ISFCN (type))
362 {
dc810e39 363 in->x_sym.x_misc.x_fsize = H_GET_32 (abfd, ext->x_sym.x_misc.x_fsize);
6fa957a9
KH
364 }
365 else
366 {
367 in->x_sym.x_misc.x_lnsz.x_lnno = GET_LNSZ_LNNO (abfd, ext);
368 in->x_sym.x_misc.x_lnsz.x_size = GET_LNSZ_SIZE (abfd, ext);
369 }
277d1b5e
ILT
370}
371
372unsigned int
7920ce38
NC
373_bfd_XXi_swap_aux_out (bfd * abfd,
374 void * inp,
375 int type,
96d56e9f 376 int in_class,
7920ce38
NC
377 int indx ATTRIBUTE_UNUSED,
378 int numaux ATTRIBUTE_UNUSED,
379 void * extp)
277d1b5e 380{
6fa957a9
KH
381 union internal_auxent *in = (union internal_auxent *) inp;
382 AUXENT *ext = (AUXENT *) extp;
383
7920ce38
NC
384 memset (ext, 0, AUXESZ);
385
96d56e9f 386 switch (in_class)
6fa957a9
KH
387 {
388 case C_FILE:
389 if (in->x_file.x_fname[0] == 0)
390 {
dc810e39
AM
391 H_PUT_32 (abfd, 0, ext->x_file.x_n.x_zeroes);
392 H_PUT_32 (abfd, in->x_file.x_n.x_offset, ext->x_file.x_n.x_offset);
6fa957a9
KH
393 }
394 else
1725a96e
NC
395 memcpy (ext->x_file.x_fname, in->x_file.x_fname, FILNMLEN);
396
277d1b5e 397 return AUXESZ;
6fa957a9
KH
398
399 case C_STAT:
400 case C_LEAFSTAT:
401 case C_HIDDEN:
402 if (type == T_NULL)
403 {
404 PUT_SCN_SCNLEN (abfd, in->x_scn.x_scnlen, ext);
405 PUT_SCN_NRELOC (abfd, in->x_scn.x_nreloc, ext);
406 PUT_SCN_NLINNO (abfd, in->x_scn.x_nlinno, ext);
dc810e39
AM
407 H_PUT_32 (abfd, in->x_scn.x_checksum, ext->x_scn.x_checksum);
408 H_PUT_16 (abfd, in->x_scn.x_associated, ext->x_scn.x_associated);
409 H_PUT_8 (abfd, in->x_scn.x_comdat, ext->x_scn.x_comdat);
6fa957a9
KH
410 return AUXESZ;
411 }
412 break;
277d1b5e 413 }
277d1b5e 414
dc810e39
AM
415 H_PUT_32 (abfd, in->x_sym.x_tagndx.l, ext->x_sym.x_tagndx);
416 H_PUT_16 (abfd, in->x_sym.x_tvndx, ext->x_sym.x_tvndx);
277d1b5e 417
96d56e9f
NC
418 if (in_class == C_BLOCK || in_class == C_FCN || ISFCN (type)
419 || ISTAG (in_class))
277d1b5e 420 {
6fa957a9
KH
421 PUT_FCN_LNNOPTR (abfd, in->x_sym.x_fcnary.x_fcn.x_lnnoptr, ext);
422 PUT_FCN_ENDNDX (abfd, in->x_sym.x_fcnary.x_fcn.x_endndx.l, ext);
277d1b5e
ILT
423 }
424 else
425 {
dc810e39
AM
426 H_PUT_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[0],
427 ext->x_sym.x_fcnary.x_ary.x_dimen[0]);
428 H_PUT_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[1],
429 ext->x_sym.x_fcnary.x_ary.x_dimen[1]);
430 H_PUT_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[2],
431 ext->x_sym.x_fcnary.x_ary.x_dimen[2]);
432 H_PUT_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[3],
433 ext->x_sym.x_fcnary.x_ary.x_dimen[3]);
277d1b5e
ILT
434 }
435
436 if (ISFCN (type))
dc810e39 437 H_PUT_32 (abfd, in->x_sym.x_misc.x_fsize, ext->x_sym.x_misc.x_fsize);
277d1b5e
ILT
438 else
439 {
440 PUT_LNSZ_LNNO (abfd, in->x_sym.x_misc.x_lnsz.x_lnno, ext);
441 PUT_LNSZ_SIZE (abfd, in->x_sym.x_misc.x_lnsz.x_size, ext);
442 }
443
444 return AUXESZ;
445}
446
447void
7920ce38 448_bfd_XXi_swap_lineno_in (bfd * abfd, void * ext1, void * in1)
277d1b5e 449{
6fa957a9
KH
450 LINENO *ext = (LINENO *) ext1;
451 struct internal_lineno *in = (struct internal_lineno *) in1;
277d1b5e 452
dc810e39 453 in->l_addr.l_symndx = H_GET_32 (abfd, ext->l_addr.l_symndx);
6fa957a9 454 in->l_lnno = GET_LINENO_LNNO (abfd, ext);
277d1b5e
ILT
455}
456
457unsigned int
7920ce38 458_bfd_XXi_swap_lineno_out (bfd * abfd, void * inp, void * outp)
277d1b5e 459{
6fa957a9
KH
460 struct internal_lineno *in = (struct internal_lineno *) inp;
461 struct external_lineno *ext = (struct external_lineno *) outp;
dc810e39 462 H_PUT_32 (abfd, in->l_addr.l_symndx, ext->l_addr.l_symndx);
277d1b5e
ILT
463
464 PUT_LINENO_LNNO (abfd, in->l_lnno, ext);
465 return LINESZ;
466}
467
468void
7920ce38
NC
469_bfd_XXi_swap_aouthdr_in (bfd * abfd,
470 void * aouthdr_ext1,
471 void * aouthdr_int1)
277d1b5e 472{
d13c9dc6 473 PEAOUTHDR * src = (PEAOUTHDR *) aouthdr_ext1;
7920ce38 474 AOUTHDR * aouthdr_ext = (AOUTHDR *) aouthdr_ext1;
d13c9dc6
L
475 struct internal_aouthdr *aouthdr_int
476 = (struct internal_aouthdr *) aouthdr_int1;
477 struct internal_extra_pe_aouthdr *a = &aouthdr_int->pe;
277d1b5e 478
dc810e39
AM
479 aouthdr_int->magic = H_GET_16 (abfd, aouthdr_ext->magic);
480 aouthdr_int->vstamp = H_GET_16 (abfd, aouthdr_ext->vstamp);
481 aouthdr_int->tsize = GET_AOUTHDR_TSIZE (abfd, aouthdr_ext->tsize);
482 aouthdr_int->dsize = GET_AOUTHDR_DSIZE (abfd, aouthdr_ext->dsize);
483 aouthdr_int->bsize = GET_AOUTHDR_BSIZE (abfd, aouthdr_ext->bsize);
484 aouthdr_int->entry = GET_AOUTHDR_ENTRY (abfd, aouthdr_ext->entry);
277d1b5e 485 aouthdr_int->text_start =
dc810e39 486 GET_AOUTHDR_TEXT_START (abfd, aouthdr_ext->text_start);
36e9d67b 487
99ad8390 488#if !defined(COFF_WITH_pep) && !defined(COFF_WITH_pex64)
7920ce38 489 /* PE32+ does not have data_start member! */
277d1b5e 490 aouthdr_int->data_start =
dc810e39 491 GET_AOUTHDR_DATA_START (abfd, aouthdr_ext->data_start);
d13c9dc6 492 a->BaseOfData = aouthdr_int->data_start;
fac41780 493#endif
277d1b5e 494
d13c9dc6
L
495 a->Magic = aouthdr_int->magic;
496 a->MajorLinkerVersion = H_GET_8 (abfd, aouthdr_ext->vstamp);
497 a->MinorLinkerVersion = H_GET_8 (abfd, aouthdr_ext->vstamp + 1);
498 a->SizeOfCode = aouthdr_int->tsize ;
499 a->SizeOfInitializedData = aouthdr_int->dsize ;
500 a->SizeOfUninitializedData = aouthdr_int->bsize ;
501 a->AddressOfEntryPoint = aouthdr_int->entry;
502 a->BaseOfCode = aouthdr_int->text_start;
dc810e39
AM
503 a->ImageBase = GET_OPTHDR_IMAGE_BASE (abfd, src->ImageBase);
504 a->SectionAlignment = H_GET_32 (abfd, src->SectionAlignment);
505 a->FileAlignment = H_GET_32 (abfd, src->FileAlignment);
277d1b5e 506 a->MajorOperatingSystemVersion =
dc810e39 507 H_GET_16 (abfd, src->MajorOperatingSystemVersion);
277d1b5e 508 a->MinorOperatingSystemVersion =
dc810e39
AM
509 H_GET_16 (abfd, src->MinorOperatingSystemVersion);
510 a->MajorImageVersion = H_GET_16 (abfd, src->MajorImageVersion);
511 a->MinorImageVersion = H_GET_16 (abfd, src->MinorImageVersion);
512 a->MajorSubsystemVersion = H_GET_16 (abfd, src->MajorSubsystemVersion);
513 a->MinorSubsystemVersion = H_GET_16 (abfd, src->MinorSubsystemVersion);
514 a->Reserved1 = H_GET_32 (abfd, src->Reserved1);
515 a->SizeOfImage = H_GET_32 (abfd, src->SizeOfImage);
516 a->SizeOfHeaders = H_GET_32 (abfd, src->SizeOfHeaders);
517 a->CheckSum = H_GET_32 (abfd, src->CheckSum);
518 a->Subsystem = H_GET_16 (abfd, src->Subsystem);
519 a->DllCharacteristics = H_GET_16 (abfd, src->DllCharacteristics);
520 a->SizeOfStackReserve =
521 GET_OPTHDR_SIZE_OF_STACK_RESERVE (abfd, src->SizeOfStackReserve);
522 a->SizeOfStackCommit =
523 GET_OPTHDR_SIZE_OF_STACK_COMMIT (abfd, src->SizeOfStackCommit);
524 a->SizeOfHeapReserve =
525 GET_OPTHDR_SIZE_OF_HEAP_RESERVE (abfd, src->SizeOfHeapReserve);
526 a->SizeOfHeapCommit =
527 GET_OPTHDR_SIZE_OF_HEAP_COMMIT (abfd, src->SizeOfHeapCommit);
528 a->LoaderFlags = H_GET_32 (abfd, src->LoaderFlags);
529 a->NumberOfRvaAndSizes = H_GET_32 (abfd, src->NumberOfRvaAndSizes);
277d1b5e
ILT
530
531 {
b24cc414 532 unsigned idx;
1725a96e 533
7e1e1988 534 /* PR 17512: Corrupt PE binaries can cause seg-faults. */
36e9d67b 535 if (a->NumberOfRvaAndSizes > IMAGE_NUMBEROF_DIRECTORY_ENTRIES)
7e1e1988 536 {
695344c0 537 /* xgettext:c-format */
4eca0228 538 _bfd_error_handler
b24cc414
AM
539 (_("%pB: aout header specifies an invalid number of"
540 " data-directory entries: %u"), abfd, a->NumberOfRvaAndSizes);
86eafac0
NC
541 bfd_set_error (bfd_error_bad_value);
542
7e1e1988
NC
543 /* Paranoia: If the number is corrupt, then assume that the
544 actual entries themselves might be corrupt as well. */
545 a->NumberOfRvaAndSizes = 0;
546 }
547
ce63b7b3 548 for (idx = 0; idx < a->NumberOfRvaAndSizes; idx++)
277d1b5e 549 {
07d6d2b8 550 /* If data directory is empty, rva also should be 0. */
6fa957a9 551 int size =
dc810e39 552 H_GET_32 (abfd, src->DataDirectory[idx][1]);
99ad8390 553
3028b4c0
DD
554 a->DataDirectory[idx].Size = size;
555
556 if (size)
1725a96e 557 a->DataDirectory[idx].VirtualAddress =
dc810e39 558 H_GET_32 (abfd, src->DataDirectory[idx][0]);
6fa957a9 559 else
3028b4c0 560 a->DataDirectory[idx].VirtualAddress = 0;
277d1b5e 561 }
36e9d67b
NC
562
563 while (idx < IMAGE_NUMBEROF_DIRECTORY_ENTRIES)
564 {
565 a->DataDirectory[idx].Size = 0;
566 a->DataDirectory[idx].VirtualAddress = 0;
567 idx ++;
568 }
277d1b5e
ILT
569 }
570
571 if (aouthdr_int->entry)
572 {
573 aouthdr_int->entry += a->ImageBase;
99ad8390 574#if !defined(COFF_WITH_pep) && !defined(COFF_WITH_pex64)
277d1b5e 575 aouthdr_int->entry &= 0xffffffff;
fac41780 576#endif
277d1b5e 577 }
1725a96e 578
9602af51 579 if (aouthdr_int->tsize)
277d1b5e
ILT
580 {
581 aouthdr_int->text_start += a->ImageBase;
99ad8390 582#if !defined(COFF_WITH_pep) && !defined(COFF_WITH_pex64)
277d1b5e 583 aouthdr_int->text_start &= 0xffffffff;
fac41780 584#endif
277d1b5e 585 }
1725a96e 586
99ad8390 587#if !defined(COFF_WITH_pep) && !defined(COFF_WITH_pex64)
7920ce38 588 /* PE32+ does not have data_start member! */
9602af51 589 if (aouthdr_int->dsize)
277d1b5e
ILT
590 {
591 aouthdr_int->data_start += a->ImageBase;
592 aouthdr_int->data_start &= 0xffffffff;
593 }
fac41780 594#endif
277d1b5e
ILT
595
596#ifdef POWERPC_LE_PE
597 /* These three fields are normally set up by ppc_relocate_section.
598 In the case of reading a file in, we can pick them up from the
599 DataDirectory. */
6c73cbb1
NC
600 first_thunk_address = a->DataDirectory[PE_IMPORT_ADDRESS_TABLE].VirtualAddress;
601 thunk_size = a->DataDirectory[PE_IMPORT_ADDRESS_TABLE].Size;
602 import_table_size = a->DataDirectory[PE_IMPORT_TABLE].Size;
277d1b5e 603#endif
277d1b5e
ILT
604}
605
5933bdc9
ILT
606/* A support function for below. */
607
608static void
7920ce38
NC
609add_data_entry (bfd * abfd,
610 struct internal_extra_pe_aouthdr *aout,
611 int idx,
612 char *name,
613 bfd_vma base)
277d1b5e
ILT
614{
615 asection *sec = bfd_get_section_by_name (abfd, name);
616
1725a96e 617 /* Add import directory information if it exists. */
277d1b5e
ILT
618 if ((sec != NULL)
619 && (coff_section_data (abfd, sec) != NULL)
620 && (pei_section_data (abfd, sec) != NULL))
621 {
1725a96e 622 /* If data directory is empty, rva also should be 0. */
3028b4c0
DD
623 int size = pei_section_data (abfd, sec)->virt_size;
624 aout->DataDirectory[idx].Size = size;
625
626 if (size)
6fa957a9
KH
627 {
628 aout->DataDirectory[idx].VirtualAddress =
629 (sec->vma - base) & 0xffffffff;
630 sec->flags |= SEC_DATA;
631 }
277d1b5e
ILT
632 }
633}
634
635unsigned int
7920ce38 636_bfd_XXi_swap_aouthdr_out (bfd * abfd, void * in, void * out)
277d1b5e 637{
6fa957a9 638 struct internal_aouthdr *aouthdr_in = (struct internal_aouthdr *) in;
cbff5e0d
DD
639 pe_data_type *pe = pe_data (abfd);
640 struct internal_extra_pe_aouthdr *extra = &pe->pe_opthdr;
6fa957a9 641 PEAOUTHDR *aouthdr_out = (PEAOUTHDR *) out;
fac41780 642 bfd_vma sa, fa, ib;
ca6dee30 643 IMAGE_DATA_DIRECTORY idata2, idata5, tls;
4e1fc599 644
fac41780
JW
645 sa = extra->SectionAlignment;
646 fa = extra->FileAlignment;
647 ib = extra->ImageBase;
277d1b5e 648
6c73cbb1
NC
649 idata2 = pe->pe_opthdr.DataDirectory[PE_IMPORT_TABLE];
650 idata5 = pe->pe_opthdr.DataDirectory[PE_IMPORT_ADDRESS_TABLE];
651 tls = pe->pe_opthdr.DataDirectory[PE_TLS_TABLE];
4e1fc599 652
9602af51 653 if (aouthdr_in->tsize)
277d1b5e
ILT
654 {
655 aouthdr_in->text_start -= ib;
99ad8390 656#if !defined(COFF_WITH_pep) && !defined(COFF_WITH_pex64)
277d1b5e 657 aouthdr_in->text_start &= 0xffffffff;
cbff5e0d 658#endif
277d1b5e 659 }
1725a96e 660
9602af51 661 if (aouthdr_in->dsize)
277d1b5e
ILT
662 {
663 aouthdr_in->data_start -= ib;
99ad8390 664#if !defined(COFF_WITH_pep) && !defined(COFF_WITH_pex64)
277d1b5e 665 aouthdr_in->data_start &= 0xffffffff;
cbff5e0d 666#endif
277d1b5e 667 }
1725a96e 668
9602af51 669 if (aouthdr_in->entry)
277d1b5e
ILT
670 {
671 aouthdr_in->entry -= ib;
99ad8390 672#if !defined(COFF_WITH_pep) && !defined(COFF_WITH_pex64)
277d1b5e 673 aouthdr_in->entry &= 0xffffffff;
cbff5e0d 674#endif
277d1b5e
ILT
675 }
676
6fa957a9
KH
677#define FA(x) (((x) + fa -1 ) & (- fa))
678#define SA(x) (((x) + sa -1 ) & (- sa))
277d1b5e 679
6fa957a9 680 /* We like to have the sizes aligned. */
277d1b5e
ILT
681 aouthdr_in->bsize = FA (aouthdr_in->bsize);
682
277d1b5e
ILT
683 extra->NumberOfRvaAndSizes = IMAGE_NUMBEROF_DIRECTORY_ENTRIES;
684
477bdd39
JT
685 add_data_entry (abfd, extra, PE_EXPORT_TABLE, ".edata", ib);
686 add_data_entry (abfd, extra, PE_RESOURCE_TABLE, ".rsrc", ib);
687 add_data_entry (abfd, extra, PE_EXCEPTION_TABLE, ".pdata", ib);
2fbadf2c 688
c25cfdf8
NC
689 /* In theory we do not need to call add_data_entry for .idata$2 or
690 .idata$5. It will be done in bfd_coff_final_link where all the
691 required information is available. If however, we are not going
692 to perform a final link, eg because we have been invoked by objcopy
693 or strip, then we need to make sure that these Data Directory
694 entries are initialised properly.
695
696 So - we copy the input values into the output values, and then, if
697 a final link is going to be performed, it can overwrite them. */
6c73cbb1
NC
698 extra->DataDirectory[PE_IMPORT_TABLE] = idata2;
699 extra->DataDirectory[PE_IMPORT_ADDRESS_TABLE] = idata5;
700 extra->DataDirectory[PE_TLS_TABLE] = tls;
c25cfdf8 701
6c73cbb1 702 if (extra->DataDirectory[PE_IMPORT_TABLE].VirtualAddress == 0)
c25cfdf8 703 /* Until other .idata fixes are made (pending patch), the entry for
7dee875e 704 .idata is needed for backwards compatibility. FIXME. */
477bdd39 705 add_data_entry (abfd, extra, PE_IMPORT_TABLE, ".idata", ib);
4e1fc599 706
2fbadf2c
ILT
707 /* For some reason, the virtual size (which is what's set by
708 add_data_entry) for .reloc is not the same as the size recorded
709 in this slot by MSVC; it doesn't seem to cause problems (so far),
710 but since it's the best we've got, use it. It does do the right
711 thing for .pdata. */
cbff5e0d 712 if (pe->has_reloc_section)
477bdd39 713 add_data_entry (abfd, extra, PE_BASE_RELOCATION_TABLE, ".reloc", ib);
277d1b5e
ILT
714
715 {
716 asection *sec;
d48bdb99 717 bfd_vma hsize = 0;
6fa957a9 718 bfd_vma dsize = 0;
d48bdb99 719 bfd_vma isize = 0;
6fa957a9 720 bfd_vma tsize = 0;
277d1b5e
ILT
721
722 for (sec = abfd->sections; sec; sec = sec->next)
723 {
7920ce38 724 int rounded = FA (sec->size);
277d1b5e 725
d48bdb99
AM
726 /* The first non-zero section filepos is the header size.
727 Sections without contents will have a filepos of 0. */
728 if (hsize == 0)
729 hsize = sec->filepos;
277d1b5e
ILT
730 if (sec->flags & SEC_DATA)
731 dsize += rounded;
732 if (sec->flags & SEC_CODE)
733 tsize += rounded;
5933bdc9
ILT
734 /* The image size is the total VIRTUAL size (which is what is
735 in the virt_size field). Files have been seen (from MSVC
736 5.0 link.exe) where the file size of the .data segment is
737 quite small compared to the virtual size. Without this
50572669
L
738 fix, strip munges the file.
739
740 FIXME: We need to handle holes between sections, which may
741 happpen when we covert from another format. We just use
742 the virtual address and virtual size of the last section
743 for the image size. */
98a96df7
CF
744 if (coff_section_data (abfd, sec) != NULL
745 && pei_section_data (abfd, sec) != NULL)
50572669
L
746 isize = (sec->vma - extra->ImageBase
747 + SA (FA (pei_section_data (abfd, sec)->virt_size)));
277d1b5e
ILT
748 }
749
750 aouthdr_in->dsize = dsize;
751 aouthdr_in->tsize = tsize;
d48bdb99 752 extra->SizeOfHeaders = hsize;
50572669 753 extra->SizeOfImage = isize;
277d1b5e
ILT
754 }
755
dc810e39 756 H_PUT_16 (abfd, aouthdr_in->magic, aouthdr_out->standard.magic);
277d1b5e 757
5fdcb63c
KT
758/* e.g. 219510000 is linker version 2.19 */
759#define LINKER_VERSION ((short) (BFD_VERSION / 1000000))
5933bdc9
ILT
760
761 /* This piece of magic sets the "linker version" field to
762 LINKER_VERSION. */
dc810e39
AM
763 H_PUT_16 (abfd, (LINKER_VERSION / 100 + (LINKER_VERSION % 100) * 256),
764 aouthdr_out->standard.vstamp);
765
766 PUT_AOUTHDR_TSIZE (abfd, aouthdr_in->tsize, aouthdr_out->standard.tsize);
767 PUT_AOUTHDR_DSIZE (abfd, aouthdr_in->dsize, aouthdr_out->standard.dsize);
768 PUT_AOUTHDR_BSIZE (abfd, aouthdr_in->bsize, aouthdr_out->standard.bsize);
769 PUT_AOUTHDR_ENTRY (abfd, aouthdr_in->entry, aouthdr_out->standard.entry);
277d1b5e 770 PUT_AOUTHDR_TEXT_START (abfd, aouthdr_in->text_start,
dc810e39 771 aouthdr_out->standard.text_start);
277d1b5e 772
99ad8390 773#if !defined(COFF_WITH_pep) && !defined(COFF_WITH_pex64)
c25cfdf8 774 /* PE32+ does not have data_start member! */
277d1b5e 775 PUT_AOUTHDR_DATA_START (abfd, aouthdr_in->data_start,
dc810e39 776 aouthdr_out->standard.data_start);
fac41780 777#endif
277d1b5e 778
dc810e39
AM
779 PUT_OPTHDR_IMAGE_BASE (abfd, extra->ImageBase, aouthdr_out->ImageBase);
780 H_PUT_32 (abfd, extra->SectionAlignment, aouthdr_out->SectionAlignment);
781 H_PUT_32 (abfd, extra->FileAlignment, aouthdr_out->FileAlignment);
782 H_PUT_16 (abfd, extra->MajorOperatingSystemVersion,
783 aouthdr_out->MajorOperatingSystemVersion);
784 H_PUT_16 (abfd, extra->MinorOperatingSystemVersion,
785 aouthdr_out->MinorOperatingSystemVersion);
786 H_PUT_16 (abfd, extra->MajorImageVersion, aouthdr_out->MajorImageVersion);
787 H_PUT_16 (abfd, extra->MinorImageVersion, aouthdr_out->MinorImageVersion);
788 H_PUT_16 (abfd, extra->MajorSubsystemVersion,
789 aouthdr_out->MajorSubsystemVersion);
790 H_PUT_16 (abfd, extra->MinorSubsystemVersion,
791 aouthdr_out->MinorSubsystemVersion);
792 H_PUT_32 (abfd, extra->Reserved1, aouthdr_out->Reserved1);
793 H_PUT_32 (abfd, extra->SizeOfImage, aouthdr_out->SizeOfImage);
794 H_PUT_32 (abfd, extra->SizeOfHeaders, aouthdr_out->SizeOfHeaders);
795 H_PUT_32 (abfd, extra->CheckSum, aouthdr_out->CheckSum);
796 H_PUT_16 (abfd, extra->Subsystem, aouthdr_out->Subsystem);
797 H_PUT_16 (abfd, extra->DllCharacteristics, aouthdr_out->DllCharacteristics);
fac41780 798 PUT_OPTHDR_SIZE_OF_STACK_RESERVE (abfd, extra->SizeOfStackReserve,
dc810e39 799 aouthdr_out->SizeOfStackReserve);
fac41780 800 PUT_OPTHDR_SIZE_OF_STACK_COMMIT (abfd, extra->SizeOfStackCommit,
dc810e39 801 aouthdr_out->SizeOfStackCommit);
fac41780 802 PUT_OPTHDR_SIZE_OF_HEAP_RESERVE (abfd, extra->SizeOfHeapReserve,
dc810e39 803 aouthdr_out->SizeOfHeapReserve);
fac41780 804 PUT_OPTHDR_SIZE_OF_HEAP_COMMIT (abfd, extra->SizeOfHeapCommit,
dc810e39
AM
805 aouthdr_out->SizeOfHeapCommit);
806 H_PUT_32 (abfd, extra->LoaderFlags, aouthdr_out->LoaderFlags);
807 H_PUT_32 (abfd, extra->NumberOfRvaAndSizes,
808 aouthdr_out->NumberOfRvaAndSizes);
277d1b5e
ILT
809 {
810 int idx;
1725a96e 811
36e9d67b 812 for (idx = 0; idx < IMAGE_NUMBEROF_DIRECTORY_ENTRIES; idx++)
277d1b5e 813 {
dc810e39
AM
814 H_PUT_32 (abfd, extra->DataDirectory[idx].VirtualAddress,
815 aouthdr_out->DataDirectory[idx][0]);
816 H_PUT_32 (abfd, extra->DataDirectory[idx].Size,
817 aouthdr_out->DataDirectory[idx][1]);
277d1b5e
ILT
818 }
819 }
820
821 return AOUTSZ;
822}
823
824unsigned int
7920ce38 825_bfd_XXi_only_swap_filehdr_out (bfd * abfd, void * in, void * out)
277d1b5e
ILT
826{
827 int idx;
6fa957a9
KH
828 struct internal_filehdr *filehdr_in = (struct internal_filehdr *) in;
829 struct external_PEI_filehdr *filehdr_out = (struct external_PEI_filehdr *) out;
277d1b5e 830
441f34fa
L
831 if (pe_data (abfd)->has_reloc_section
832 || pe_data (abfd)->dont_strip_reloc)
277d1b5e
ILT
833 filehdr_in->f_flags &= ~F_RELFLG;
834
835 if (pe_data (abfd)->dll)
836 filehdr_in->f_flags |= F_DLL;
837
830db048 838 filehdr_in->pe.e_magic = IMAGE_DOS_SIGNATURE;
277d1b5e
ILT
839 filehdr_in->pe.e_cblp = 0x90;
840 filehdr_in->pe.e_cp = 0x3;
841 filehdr_in->pe.e_crlc = 0x0;
842 filehdr_in->pe.e_cparhdr = 0x4;
843 filehdr_in->pe.e_minalloc = 0x0;
844 filehdr_in->pe.e_maxalloc = 0xffff;
845 filehdr_in->pe.e_ss = 0x0;
846 filehdr_in->pe.e_sp = 0xb8;
847 filehdr_in->pe.e_csum = 0x0;
848 filehdr_in->pe.e_ip = 0x0;
849 filehdr_in->pe.e_cs = 0x0;
850 filehdr_in->pe.e_lfarlc = 0x40;
851 filehdr_in->pe.e_ovno = 0x0;
852
6fa957a9 853 for (idx = 0; idx < 4; idx++)
277d1b5e
ILT
854 filehdr_in->pe.e_res[idx] = 0x0;
855
856 filehdr_in->pe.e_oemid = 0x0;
857 filehdr_in->pe.e_oeminfo = 0x0;
858
6fa957a9 859 for (idx = 0; idx < 10; idx++)
277d1b5e
ILT
860 filehdr_in->pe.e_res2[idx] = 0x0;
861
862 filehdr_in->pe.e_lfanew = 0x80;
863
6fa957a9
KH
864 /* This next collection of data are mostly just characters. It
865 appears to be constant within the headers put on NT exes. */
277d1b5e
ILT
866 filehdr_in->pe.dos_message[0] = 0x0eba1f0e;
867 filehdr_in->pe.dos_message[1] = 0xcd09b400;
868 filehdr_in->pe.dos_message[2] = 0x4c01b821;
869 filehdr_in->pe.dos_message[3] = 0x685421cd;
870 filehdr_in->pe.dos_message[4] = 0x70207369;
871 filehdr_in->pe.dos_message[5] = 0x72676f72;
872 filehdr_in->pe.dos_message[6] = 0x63206d61;
873 filehdr_in->pe.dos_message[7] = 0x6f6e6e61;
874 filehdr_in->pe.dos_message[8] = 0x65622074;
875 filehdr_in->pe.dos_message[9] = 0x6e757220;
876 filehdr_in->pe.dos_message[10] = 0x206e6920;
877 filehdr_in->pe.dos_message[11] = 0x20534f44;
878 filehdr_in->pe.dos_message[12] = 0x65646f6d;
879 filehdr_in->pe.dos_message[13] = 0x0a0d0d2e;
880 filehdr_in->pe.dos_message[14] = 0x24;
881 filehdr_in->pe.dos_message[15] = 0x0;
830db048 882 filehdr_in->pe.nt_signature = IMAGE_NT_SIGNATURE;
277d1b5e 883
dc810e39
AM
884 H_PUT_16 (abfd, filehdr_in->f_magic, filehdr_out->f_magic);
885 H_PUT_16 (abfd, filehdr_in->f_nscns, filehdr_out->f_nscns);
277d1b5e 886
dfbfec24
BW
887 /* Use a real timestamp by default, unless the no-insert-timestamp
888 option was chosen. */
0cb112f7 889 if ((pe_data (abfd)->insert_timestamp))
61e2488c 890 H_PUT_32 (abfd, time (0), filehdr_out->f_timdat);
1c5f704f
NC
891 else
892 H_PUT_32 (abfd, 0, filehdr_out->f_timdat);
0cb112f7 893
dc810e39
AM
894 PUT_FILEHDR_SYMPTR (abfd, filehdr_in->f_symptr,
895 filehdr_out->f_symptr);
896 H_PUT_32 (abfd, filehdr_in->f_nsyms, filehdr_out->f_nsyms);
897 H_PUT_16 (abfd, filehdr_in->f_opthdr, filehdr_out->f_opthdr);
898 H_PUT_16 (abfd, filehdr_in->f_flags, filehdr_out->f_flags);
277d1b5e 899
1725a96e 900 /* Put in extra dos header stuff. This data remains essentially
277d1b5e 901 constant, it just has to be tacked on to the beginning of all exes
1725a96e 902 for NT. */
dc810e39
AM
903 H_PUT_16 (abfd, filehdr_in->pe.e_magic, filehdr_out->e_magic);
904 H_PUT_16 (abfd, filehdr_in->pe.e_cblp, filehdr_out->e_cblp);
905 H_PUT_16 (abfd, filehdr_in->pe.e_cp, filehdr_out->e_cp);
906 H_PUT_16 (abfd, filehdr_in->pe.e_crlc, filehdr_out->e_crlc);
907 H_PUT_16 (abfd, filehdr_in->pe.e_cparhdr, filehdr_out->e_cparhdr);
908 H_PUT_16 (abfd, filehdr_in->pe.e_minalloc, filehdr_out->e_minalloc);
909 H_PUT_16 (abfd, filehdr_in->pe.e_maxalloc, filehdr_out->e_maxalloc);
910 H_PUT_16 (abfd, filehdr_in->pe.e_ss, filehdr_out->e_ss);
911 H_PUT_16 (abfd, filehdr_in->pe.e_sp, filehdr_out->e_sp);
912 H_PUT_16 (abfd, filehdr_in->pe.e_csum, filehdr_out->e_csum);
913 H_PUT_16 (abfd, filehdr_in->pe.e_ip, filehdr_out->e_ip);
914 H_PUT_16 (abfd, filehdr_in->pe.e_cs, filehdr_out->e_cs);
915 H_PUT_16 (abfd, filehdr_in->pe.e_lfarlc, filehdr_out->e_lfarlc);
916 H_PUT_16 (abfd, filehdr_in->pe.e_ovno, filehdr_out->e_ovno);
1725a96e
NC
917
918 for (idx = 0; idx < 4; idx++)
dc810e39 919 H_PUT_16 (abfd, filehdr_in->pe.e_res[idx], filehdr_out->e_res[idx]);
1725a96e 920
dc810e39
AM
921 H_PUT_16 (abfd, filehdr_in->pe.e_oemid, filehdr_out->e_oemid);
922 H_PUT_16 (abfd, filehdr_in->pe.e_oeminfo, filehdr_out->e_oeminfo);
1725a96e
NC
923
924 for (idx = 0; idx < 10; idx++)
dc810e39 925 H_PUT_16 (abfd, filehdr_in->pe.e_res2[idx], filehdr_out->e_res2[idx]);
1725a96e 926
dc810e39 927 H_PUT_32 (abfd, filehdr_in->pe.e_lfanew, filehdr_out->e_lfanew);
277d1b5e 928
1725a96e 929 for (idx = 0; idx < 16; idx++)
dc810e39
AM
930 H_PUT_32 (abfd, filehdr_in->pe.dos_message[idx],
931 filehdr_out->dos_message[idx]);
277d1b5e 932
6fa957a9 933 /* Also put in the NT signature. */
dc810e39 934 H_PUT_32 (abfd, filehdr_in->pe.nt_signature, filehdr_out->nt_signature);
277d1b5e 935
277d1b5e
ILT
936 return FILHSZ;
937}
938
939unsigned int
7920ce38 940_bfd_XX_only_swap_filehdr_out (bfd * abfd, void * in, void * out)
277d1b5e 941{
6fa957a9
KH
942 struct internal_filehdr *filehdr_in = (struct internal_filehdr *) in;
943 FILHDR *filehdr_out = (FILHDR *) out;
277d1b5e 944
dc810e39
AM
945 H_PUT_16 (abfd, filehdr_in->f_magic, filehdr_out->f_magic);
946 H_PUT_16 (abfd, filehdr_in->f_nscns, filehdr_out->f_nscns);
947 H_PUT_32 (abfd, filehdr_in->f_timdat, filehdr_out->f_timdat);
948 PUT_FILEHDR_SYMPTR (abfd, filehdr_in->f_symptr, filehdr_out->f_symptr);
949 H_PUT_32 (abfd, filehdr_in->f_nsyms, filehdr_out->f_nsyms);
950 H_PUT_16 (abfd, filehdr_in->f_opthdr, filehdr_out->f_opthdr);
951 H_PUT_16 (abfd, filehdr_in->f_flags, filehdr_out->f_flags);
277d1b5e
ILT
952
953 return FILHSZ;
954}
955
956unsigned int
7920ce38 957_bfd_XXi_swap_scnhdr_out (bfd * abfd, void * in, void * out)
277d1b5e 958{
6fa957a9
KH
959 struct internal_scnhdr *scnhdr_int = (struct internal_scnhdr *) in;
960 SCNHDR *scnhdr_ext = (SCNHDR *) out;
277d1b5e
ILT
961 unsigned int ret = SCNHSZ;
962 bfd_vma ps;
963 bfd_vma ss;
964
6fa957a9 965 memcpy (scnhdr_ext->s_name, scnhdr_int->s_name, sizeof (scnhdr_int->s_name));
277d1b5e
ILT
966
967 PUT_SCNHDR_VADDR (abfd,
9602af51 968 ((scnhdr_int->s_vaddr
6fa957a9 969 - pe_data (abfd)->pe_opthdr.ImageBase)
277d1b5e 970 & 0xffffffff),
dc810e39 971 scnhdr_ext->s_vaddr);
277d1b5e 972
5933bdc9
ILT
973 /* NT wants the size data to be rounded up to the next
974 NT_FILE_ALIGNMENT, but zero if it has no content (as in .bss,
975 sometimes). */
5933bdc9 976 if ((scnhdr_int->s_flags & IMAGE_SCN_CNT_UNINITIALIZED_DATA) != 0)
277d1b5e 977 {
92dd4511 978 if (bfd_pei_p (abfd))
ff0c9faf
NC
979 {
980 ps = scnhdr_int->s_size;
981 ss = 0;
982 }
983 else
984 {
07d6d2b8
AM
985 ps = 0;
986 ss = scnhdr_int->s_size;
ff0c9faf 987 }
277d1b5e
ILT
988 }
989 else
990 {
92dd4511 991 if (bfd_pei_p (abfd))
ff0c9faf
NC
992 ps = scnhdr_int->s_paddr;
993 else
994 ps = 0;
995
277d1b5e
ILT
996 ss = scnhdr_int->s_size;
997 }
998
999 PUT_SCNHDR_SIZE (abfd, ss,
dc810e39 1000 scnhdr_ext->s_size);
277d1b5e 1001
5933bdc9 1002 /* s_paddr in PE is really the virtual size. */
dc810e39 1003 PUT_SCNHDR_PADDR (abfd, ps, scnhdr_ext->s_paddr);
277d1b5e
ILT
1004
1005 PUT_SCNHDR_SCNPTR (abfd, scnhdr_int->s_scnptr,
dc810e39 1006 scnhdr_ext->s_scnptr);
277d1b5e 1007 PUT_SCNHDR_RELPTR (abfd, scnhdr_int->s_relptr,
dc810e39 1008 scnhdr_ext->s_relptr);
277d1b5e 1009 PUT_SCNHDR_LNNOPTR (abfd, scnhdr_int->s_lnnoptr,
dc810e39 1010 scnhdr_ext->s_lnnoptr);
277d1b5e 1011
277d1b5e 1012 {
25c80428
NC
1013 /* Extra flags must be set when dealing with PE. All sections should also
1014 have the IMAGE_SCN_MEM_READ (0x40000000) flag set. In addition, the
1015 .text section must have IMAGE_SCN_MEM_EXECUTE (0x20000000) and the data
1016 sections (.idata, .data, .bss, .CRT) must have IMAGE_SCN_MEM_WRITE set
1017 (this is especially important when dealing with the .idata section since
1018 the addresses for routines from .dlls must be overwritten). If .reloc
1019 section data is ever generated, we must add IMAGE_SCN_MEM_DISCARDABLE
1020 (0x02000000). Also, the resource data should also be read and
1021 writable. */
1022
4e1fc599 1023 /* FIXME: Alignment is also encoded in this field, at least on PPC and
25c80428
NC
1024 ARM-WINCE. Although - how do we get the original alignment field
1025 back ? */
1026
1027 typedef struct
1028 {
7bd8862c 1029 char section_name[SCNNMLEN];
25c80428
NC
1030 unsigned long must_have;
1031 }
1032 pe_required_section_flags;
4e1fc599 1033
25c80428
NC
1034 pe_required_section_flags known_sections [] =
1035 {
1036 { ".arch", IMAGE_SCN_MEM_READ | IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_MEM_DISCARDABLE | IMAGE_SCN_ALIGN_8BYTES },
1037 { ".bss", IMAGE_SCN_MEM_READ | IMAGE_SCN_CNT_UNINITIALIZED_DATA | IMAGE_SCN_MEM_WRITE },
1038 { ".data", IMAGE_SCN_MEM_READ | IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_MEM_WRITE },
1039 { ".edata", IMAGE_SCN_MEM_READ | IMAGE_SCN_CNT_INITIALIZED_DATA },
1040 { ".idata", IMAGE_SCN_MEM_READ | IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_MEM_WRITE },
1041 { ".pdata", IMAGE_SCN_MEM_READ | IMAGE_SCN_CNT_INITIALIZED_DATA },
1042 { ".rdata", IMAGE_SCN_MEM_READ | IMAGE_SCN_CNT_INITIALIZED_DATA },
1043 { ".reloc", IMAGE_SCN_MEM_READ | IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_MEM_DISCARDABLE },
1044 { ".rsrc", IMAGE_SCN_MEM_READ | IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_MEM_WRITE },
1045 { ".text" , IMAGE_SCN_MEM_READ | IMAGE_SCN_CNT_CODE | IMAGE_SCN_MEM_EXECUTE },
1046 { ".tls", IMAGE_SCN_MEM_READ | IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_MEM_WRITE },
1047 { ".xdata", IMAGE_SCN_MEM_READ | IMAGE_SCN_CNT_INITIALIZED_DATA },
25c80428
NC
1048 };
1049
1050 pe_required_section_flags * p;
1725a96e 1051
66bed356
DS
1052 /* We have defaulted to adding the IMAGE_SCN_MEM_WRITE flag, but now
1053 we know exactly what this specific section wants so we remove it
1054 and then allow the must_have field to add it back in if necessary.
1055 However, we don't remove IMAGE_SCN_MEM_WRITE flag from .text if the
1056 default WP_TEXT file flag has been cleared. WP_TEXT may be cleared
1057 by ld --enable-auto-import (if auto-import is actually needed),
1058 by ld --omagic, or by obcopy --writable-text. */
66bed356 1059
7bd8862c
AM
1060 for (p = known_sections;
1061 p < known_sections + ARRAY_SIZE (known_sections);
1062 p++)
1063 if (memcmp (scnhdr_int->s_name, p->section_name, SCNNMLEN) == 0)
25c80428 1064 {
7bd8862c 1065 if (memcmp (scnhdr_int->s_name, ".text", sizeof ".text")
3c9d0484 1066 || (bfd_get_file_flags (abfd) & WP_TEXT))
d48bdb99
AM
1067 scnhdr_int->s_flags &= ~IMAGE_SCN_MEM_WRITE;
1068 scnhdr_int->s_flags |= p->must_have;
25c80428
NC
1069 break;
1070 }
1071
d48bdb99 1072 H_PUT_32 (abfd, scnhdr_int->s_flags, scnhdr_ext->s_flags);
277d1b5e
ILT
1073 }
1074
cb43721d 1075 if (coff_data (abfd)->link_info
0e1862bb
L
1076 && ! bfd_link_relocatable (coff_data (abfd)->link_info)
1077 && ! bfd_link_pic (coff_data (abfd)->link_info)
7bd8862c 1078 && memcmp (scnhdr_int->s_name, ".text", sizeof ".text") == 0)
277d1b5e 1079 {
cb43721d 1080 /* By inference from looking at MS output, the 32 bit field
7dee875e 1081 which is the combination of the number_of_relocs and
cb43721d
ILT
1082 number_of_linenos is used for the line number count in
1083 executables. A 16-bit field won't do for cc1. The MS
1084 document says that the number of relocs is zero for
1085 executables, but the 17-th bit has been observed to be there.
1086 Overflow is not an issue: a 4G-line program will overflow a
1087 bunch of other fields long before this! */
dc810e39
AM
1088 H_PUT_16 (abfd, (scnhdr_int->s_nlnno & 0xffff), scnhdr_ext->s_nlnno);
1089 H_PUT_16 (abfd, (scnhdr_int->s_nlnno >> 16), scnhdr_ext->s_nreloc);
277d1b5e 1090 }
277d1b5e
ILT
1091 else
1092 {
cb43721d 1093 if (scnhdr_int->s_nlnno <= 0xffff)
dc810e39 1094 H_PUT_16 (abfd, scnhdr_int->s_nlnno, scnhdr_ext->s_nlnno);
cb43721d
ILT
1095 else
1096 {
695344c0 1097 /* xgettext:c-format */
871b3ab2 1098 _bfd_error_handler (_("%pB: line number overflow: 0x%lx > 0xffff"),
dae82561 1099 abfd, scnhdr_int->s_nlnno);
cb43721d 1100 bfd_set_error (bfd_error_file_truncated);
dc810e39 1101 H_PUT_16 (abfd, 0xffff, scnhdr_ext->s_nlnno);
cb43721d
ILT
1102 ret = 0;
1103 }
1725a96e 1104
cd339148 1105 /* Although we could encode 0xffff relocs here, we do not, to be
07d6d2b8
AM
1106 consistent with other parts of bfd. Also it lets us warn, as
1107 we should never see 0xffff here w/o having the overflow flag
1108 set. */
cd339148 1109 if (scnhdr_int->s_nreloc < 0xffff)
dc810e39 1110 H_PUT_16 (abfd, scnhdr_int->s_nreloc, scnhdr_ext->s_nreloc);
cb43721d
ILT
1111 else
1112 {
1725a96e 1113 /* PE can deal with large #s of relocs, but not here. */
dc810e39 1114 H_PUT_16 (abfd, 0xffff, scnhdr_ext->s_nreloc);
3e4554a2 1115 scnhdr_int->s_flags |= IMAGE_SCN_LNK_NRELOC_OVFL;
dc810e39 1116 H_PUT_32 (abfd, scnhdr_int->s_flags, scnhdr_ext->s_flags);
cb43721d 1117 }
277d1b5e
ILT
1118 }
1119 return ret;
1120}
1121
61e2488c
JT
1122void
1123_bfd_XXi_swap_debugdir_in (bfd * abfd, void * ext1, void * in1)
1124{
1125 struct external_IMAGE_DEBUG_DIRECTORY *ext = (struct external_IMAGE_DEBUG_DIRECTORY *) ext1;
1126 struct internal_IMAGE_DEBUG_DIRECTORY *in = (struct internal_IMAGE_DEBUG_DIRECTORY *) in1;
1127
1128 in->Characteristics = H_GET_32(abfd, ext->Characteristics);
1129 in->TimeDateStamp = H_GET_32(abfd, ext->TimeDateStamp);
1130 in->MajorVersion = H_GET_16(abfd, ext->MajorVersion);
1131 in->MinorVersion = H_GET_16(abfd, ext->MinorVersion);
1132 in->Type = H_GET_32(abfd, ext->Type);
1133 in->SizeOfData = H_GET_32(abfd, ext->SizeOfData);
1134 in->AddressOfRawData = H_GET_32(abfd, ext->AddressOfRawData);
1135 in->PointerToRawData = H_GET_32(abfd, ext->PointerToRawData);
1136}
1137
1138unsigned int
1139_bfd_XXi_swap_debugdir_out (bfd * abfd, void * inp, void * extp)
1140{
1141 struct external_IMAGE_DEBUG_DIRECTORY *ext = (struct external_IMAGE_DEBUG_DIRECTORY *) extp;
1142 struct internal_IMAGE_DEBUG_DIRECTORY *in = (struct internal_IMAGE_DEBUG_DIRECTORY *) inp;
1143
1144 H_PUT_32(abfd, in->Characteristics, ext->Characteristics);
1145 H_PUT_32(abfd, in->TimeDateStamp, ext->TimeDateStamp);
1146 H_PUT_16(abfd, in->MajorVersion, ext->MajorVersion);
1147 H_PUT_16(abfd, in->MinorVersion, ext->MinorVersion);
1148 H_PUT_32(abfd, in->Type, ext->Type);
1149 H_PUT_32(abfd, in->SizeOfData, ext->SizeOfData);
1150 H_PUT_32(abfd, in->AddressOfRawData, ext->AddressOfRawData);
1151 H_PUT_32(abfd, in->PointerToRawData, ext->PointerToRawData);
1152
1153 return sizeof (struct external_IMAGE_DEBUG_DIRECTORY);
1154}
1155
c74f7d1c 1156CODEVIEW_INFO *
61e2488c
JT
1157_bfd_XXi_slurp_codeview_record (bfd * abfd, file_ptr where, unsigned long length, CODEVIEW_INFO *cvinfo)
1158{
1159 char buffer[256+1];
1160
1161 if (bfd_seek (abfd, where, SEEK_SET) != 0)
1162 return NULL;
1163
1164 if (bfd_bread (buffer, 256, abfd) < 4)
1165 return NULL;
1166
6e6e7cfc 1167 /* Ensure null termination of filename. */
61e2488c
JT
1168 buffer[256] = '\0';
1169
77ef8654 1170 cvinfo->CVSignature = H_GET_32 (abfd, buffer);
61e2488c
JT
1171 cvinfo->Age = 0;
1172
1173 if ((cvinfo->CVSignature == CVINFO_PDB70_CVSIGNATURE)
1174 && (length > sizeof (CV_INFO_PDB70)))
1175 {
1176 CV_INFO_PDB70 *cvinfo70 = (CV_INFO_PDB70 *)(buffer);
1177
1178 cvinfo->Age = H_GET_32(abfd, cvinfo70->Age);
6e6e7cfc
JT
1179
1180 /* A GUID consists of 4,2,2 byte values in little-endian order, followed
07d6d2b8
AM
1181 by 8 single bytes. Byte swap them so we can conveniently treat the GUID
1182 as 16 bytes in big-endian order. */
6e6e7cfc
JT
1183 bfd_putb32 (bfd_getl32 (cvinfo70->Signature), cvinfo->Signature);
1184 bfd_putb16 (bfd_getl16 (&(cvinfo70->Signature[4])), &(cvinfo->Signature[4]));
1185 bfd_putb16 (bfd_getl16 (&(cvinfo70->Signature[6])), &(cvinfo->Signature[6]));
1186 memcpy (&(cvinfo->Signature[8]), &(cvinfo70->Signature[8]), 8);
1187
61e2488c
JT
1188 cvinfo->SignatureLength = CV_INFO_SIGNATURE_LENGTH;
1189 // cvinfo->PdbFileName = cvinfo70->PdbFileName;
1190
1191 return cvinfo;
1192 }
1193 else if ((cvinfo->CVSignature == CVINFO_PDB20_CVSIGNATURE)
07d6d2b8 1194 && (length > sizeof (CV_INFO_PDB20)))
61e2488c
JT
1195 {
1196 CV_INFO_PDB20 *cvinfo20 = (CV_INFO_PDB20 *)(buffer);
1197 cvinfo->Age = H_GET_32(abfd, cvinfo20->Age);
1198 memcpy (cvinfo->Signature, cvinfo20->Signature, 4);
1199 cvinfo->SignatureLength = 4;
1200 // cvinfo->PdbFileName = cvinfo20->PdbFileName;
1201
1202 return cvinfo;
1203 }
1204
1205 return NULL;
1206}
1207
1208unsigned int
1209_bfd_XXi_write_codeview_record (bfd * abfd, file_ptr where, CODEVIEW_INFO *cvinfo)
1210{
7769fa97
NC
1211 const bfd_size_type size = sizeof (CV_INFO_PDB70) + 1;
1212 bfd_size_type written;
61e2488c 1213 CV_INFO_PDB70 *cvinfo70;
7769fa97 1214 char * buffer;
61e2488c
JT
1215
1216 if (bfd_seek (abfd, where, SEEK_SET) != 0)
1217 return 0;
1218
7769fa97 1219 buffer = xmalloc (size);
61e2488c
JT
1220 cvinfo70 = (CV_INFO_PDB70 *) buffer;
1221 H_PUT_32 (abfd, CVINFO_PDB70_CVSIGNATURE, cvinfo70->CvSignature);
6e6e7cfc
JT
1222
1223 /* Byte swap the GUID from 16 bytes in big-endian order to 4,2,2 byte values
1224 in little-endian order, followed by 8 single bytes. */
1225 bfd_putl32 (bfd_getb32 (cvinfo->Signature), cvinfo70->Signature);
1226 bfd_putl16 (bfd_getb16 (&(cvinfo->Signature[4])), &(cvinfo70->Signature[4]));
1227 bfd_putl16 (bfd_getb16 (&(cvinfo->Signature[6])), &(cvinfo70->Signature[6]));
1228 memcpy (&(cvinfo70->Signature[8]), &(cvinfo->Signature[8]), 8);
1229
61e2488c
JT
1230 H_PUT_32 (abfd, cvinfo->Age, cvinfo70->Age);
1231 cvinfo70->PdbFileName[0] = '\0';
1232
7769fa97
NC
1233 written = bfd_bwrite (buffer, size, abfd);
1234
1235 free (buffer);
61e2488c 1236
7769fa97 1237 return written == size ? size : 0;
61e2488c
JT
1238}
1239
1725a96e 1240static char * dir_names[IMAGE_NUMBEROF_DIRECTORY_ENTRIES] =
7920ce38
NC
1241{
1242 N_("Export Directory [.edata (or where ever we found it)]"),
1243 N_("Import Directory [parts of .idata]"),
1244 N_("Resource Directory [.rsrc]"),
1245 N_("Exception Directory [.pdata]"),
1246 N_("Security Directory"),
1247 N_("Base Relocation Directory [.reloc]"),
1248 N_("Debug Directory"),
1249 N_("Description Directory"),
1250 N_("Special Directory"),
1251 N_("Thread Storage Directory [.tls]"),
1252 N_("Load Configuration Directory"),
1253 N_("Bound Import Directory"),
1254 N_("Import Address Table Directory"),
1255 N_("Delay Import Directory"),
6c73cbb1 1256 N_("CLR Runtime Header"),
7920ce38
NC
1257 N_("Reserved")
1258};
1725a96e 1259
277d1b5e
ILT
1260#ifdef POWERPC_LE_PE
1261/* The code for the PPC really falls in the "architecture dependent"
1262 category. However, it's not clear that anyone will ever care, so
1263 we're ignoring the issue for now; if/when PPC matters, some of this
1264 may need to go into peicode.h, or arguments passed to enable the
1265 PPC- specific code. */
1266#endif
1267
b34976b6 1268static bfd_boolean
7920ce38 1269pe_print_idata (bfd * abfd, void * vfile)
277d1b5e
ILT
1270{
1271 FILE *file = (FILE *) vfile;
a76b448c 1272 bfd_byte *data;
8181c403
AM
1273 asection *section;
1274 bfd_signed_vma adj;
277d1b5e
ILT
1275
1276#ifdef POWERPC_LE_PE
1277 asection *rel_section = bfd_get_section_by_name (abfd, ".reldata");
1278#endif
1279
a76b448c 1280 bfd_size_type datasize = 0;
277d1b5e 1281 bfd_size_type dataoff;
277d1b5e 1282 bfd_size_type i;
277d1b5e
ILT
1283 int onaline = 20;
1284
1285 pe_data_type *pe = pe_data (abfd);
1286 struct internal_extra_pe_aouthdr *extra = &pe->pe_opthdr;
1287
8181c403 1288 bfd_vma addr;
277d1b5e 1289
6c73cbb1 1290 addr = extra->DataDirectory[PE_IMPORT_TABLE].VirtualAddress;
277d1b5e 1291
6c73cbb1 1292 if (addr == 0 && extra->DataDirectory[PE_IMPORT_TABLE].Size == 0)
8181c403 1293 {
a76b448c
AM
1294 /* Maybe the extra header isn't there. Look for the section. */
1295 section = bfd_get_section_by_name (abfd, ".idata");
1296 if (section == NULL)
b34976b6 1297 return TRUE;
a76b448c
AM
1298
1299 addr = section->vma;
eea6121a 1300 datasize = section->size;
a76b448c 1301 if (datasize == 0)
b34976b6 1302 return TRUE;
8181c403 1303 }
a76b448c 1304 else
8181c403 1305 {
a76b448c
AM
1306 addr += extra->ImageBase;
1307 for (section = abfd->sections; section != NULL; section = section->next)
1308 {
eea6121a 1309 datasize = section->size;
a76b448c
AM
1310 if (addr >= section->vma && addr < section->vma + datasize)
1311 break;
1312 }
1313
1314 if (section == NULL)
1315 {
1316 fprintf (file,
1317 _("\nThere is an import table, but the section containing it could not be found\n"));
b34976b6 1318 return TRUE;
a76b448c 1319 }
b69c8728 1320 else if (!(section->flags & SEC_HAS_CONTENTS))
07d6d2b8 1321 {
b69c8728
JT
1322 fprintf (file,
1323 _("\nThere is an import table in %s, but that section has no contents\n"),
1324 section->name);
1325 return TRUE;
07d6d2b8 1326 }
8181c403 1327 }
5933bdc9 1328
695344c0 1329 /* xgettext:c-format */
8181c403
AM
1330 fprintf (file, _("\nThere is an import table in %s at 0x%lx\n"),
1331 section->name, (unsigned long) addr);
277d1b5e 1332
8181c403 1333 dataoff = addr - section->vma;
277d1b5e
ILT
1334
1335#ifdef POWERPC_LE_PE
eea6121a 1336 if (rel_section != 0 && rel_section->size != 0)
277d1b5e
ILT
1337 {
1338 /* The toc address can be found by taking the starting address,
1339 which on the PPC locates a function descriptor. The
1340 descriptor consists of the function code starting address
1341 followed by the address of the toc. The starting address we
1342 get from the bfd, and the descriptor is supposed to be in the
1343 .reldata section. */
1344
1345 bfd_vma loadable_toc_address;
1346 bfd_vma toc_address;
1347 bfd_vma start_address;
eea6121a 1348 bfd_byte *data;
a50b2160 1349 bfd_vma offset;
8181c403 1350
eea6121a
AM
1351 if (!bfd_malloc_and_get_section (abfd, rel_section, &data))
1352 {
1353 if (data != NULL)
1354 free (data);
1355 return FALSE;
1356 }
277d1b5e
ILT
1357
1358 offset = abfd->start_address - rel_section->vma;
1359
a50b2160 1360 if (offset >= rel_section->size || offset + 8 > rel_section->size)
07d6d2b8
AM
1361 {
1362 if (data != NULL)
1363 free (data);
1364 return FALSE;
1365 }
a50b2160 1366
db8503c4
AM
1367 start_address = bfd_get_32 (abfd, data + offset);
1368 loadable_toc_address = bfd_get_32 (abfd, data + offset + 4);
277d1b5e
ILT
1369 toc_address = loadable_toc_address - 32768;
1370
9602af51 1371 fprintf (file,
6fa957a9
KH
1372 _("\nFunction descriptor located at the start address: %04lx\n"),
1373 (unsigned long int) (abfd->start_address));
277d1b5e 1374 fprintf (file,
695344c0 1375 /* xgettext:c-format */
277d1b5e
ILT
1376 _("\tcode-base %08lx toc (loadable/actual) %08lx/%08lx\n"),
1377 start_address, loadable_toc_address, toc_address);
eea6121a
AM
1378 if (data != NULL)
1379 free (data);
277d1b5e
ILT
1380 }
1381 else
1382 {
9602af51 1383 fprintf (file,
6fa957a9 1384 _("\nNo reldata section! Function descriptor not decoded.\n"));
277d1b5e
ILT
1385 }
1386#endif
1387
9602af51 1388 fprintf (file,
6fa957a9
KH
1389 _("\nThe Import Tables (interpreted %s section contents)\n"),
1390 section->name);
9602af51 1391 fprintf (file,
ca09e32b
NC
1392 _("\
1393 vma: Hint Time Forward DLL First\n\
1394 Table Stamp Chain Name Thunk\n"));
277d1b5e 1395
db8503c4 1396 /* Read the whole section. Some of the fields might be before dataoff. */
eea6121a
AM
1397 if (!bfd_malloc_and_get_section (abfd, section, &data))
1398 {
1399 if (data != NULL)
1400 free (data);
1401 return FALSE;
1402 }
277d1b5e 1403
db8503c4 1404 adj = section->vma - extra->ImageBase;
277d1b5e 1405
5e226794 1406 /* Print all image import descriptors. */
4e1fc599 1407 for (i = dataoff; i + onaline <= datasize; i += onaline)
277d1b5e
ILT
1408 {
1409 bfd_vma hint_addr;
1410 bfd_vma time_stamp;
1411 bfd_vma forward_chain;
1412 bfd_vma dll_name;
1413 bfd_vma first_thunk;
1414 int idx = 0;
1415 bfd_size_type j;
1416 char *dll;
1417
6c73cbb1 1418 /* Print (i + extra->DataDirectory[PE_IMPORT_TABLE].VirtualAddress). */
4e1fc599
AM
1419 fprintf (file, " %08lx\t", (unsigned long) (i + adj));
1420 hint_addr = bfd_get_32 (abfd, data + i);
1421 time_stamp = bfd_get_32 (abfd, data + i + 4);
1422 forward_chain = bfd_get_32 (abfd, data + i + 8);
1423 dll_name = bfd_get_32 (abfd, data + i + 12);
1424 first_thunk = bfd_get_32 (abfd, data + i + 16);
5933bdc9
ILT
1425
1426 fprintf (file, "%08lx %08lx %08lx %08lx %08lx\n",
a76b448c
AM
1427 (unsigned long) hint_addr,
1428 (unsigned long) time_stamp,
1429 (unsigned long) forward_chain,
1430 (unsigned long) dll_name,
1431 (unsigned long) first_thunk);
277d1b5e
ILT
1432
1433 if (hint_addr == 0 && first_thunk == 0)
1434 break;
1435
a50b2160 1436 if (dll_name - adj >= section->size)
07d6d2b8 1437 break;
a50b2160 1438
8181c403 1439 dll = (char *) data + dll_name - adj;
36e9d67b
NC
1440 /* PR 17512 file: 078-12277-0.004. */
1441 bfd_size_type maxlen = (char *)(data + datasize) - dll - 1;
1442 fprintf (file, _("\n\tDLL Name: %.*s\n"), (int) maxlen, dll);
277d1b5e 1443
9949827b
DBR
1444 /* PR 21546: When the Hint Address is zero,
1445 we try the First Thunk instead. */
1446 if (hint_addr == 0)
1447 hint_addr = first_thunk;
1448
53db9cf9 1449 if (hint_addr != 0 && hint_addr - adj < datasize)
277d1b5e 1450 {
6e7c73dd
CF
1451 bfd_byte *ft_data;
1452 asection *ft_section;
1453 bfd_vma ft_addr;
1454 bfd_size_type ft_datasize;
1455 int ft_idx;
4e1fc599 1456 int ft_allocated;
6e7c73dd 1457
5e226794 1458 fprintf (file, _("\tvma: Hint/Ord Member-Name Bound-To\n"));
277d1b5e 1459
8181c403 1460 idx = hint_addr - adj;
4e1fc599 1461
5e226794 1462 ft_addr = first_thunk + extra->ImageBase;
6e7c73dd 1463 ft_idx = first_thunk - adj;
4e1fc599
AM
1464 ft_data = data + ft_idx;
1465 ft_datasize = datasize - ft_idx;
1466 ft_allocated = 0;
6c73cbb1
NC
1467
1468 if (first_thunk != hint_addr)
6e7c73dd
CF
1469 {
1470 /* Find the section which contains the first thunk. */
1471 for (ft_section = abfd->sections;
1472 ft_section != NULL;
1473 ft_section = ft_section->next)
1474 {
6e7c73dd 1475 if (ft_addr >= ft_section->vma
4e1fc599 1476 && ft_addr < ft_section->vma + ft_section->size)
6e7c73dd
CF
1477 break;
1478 }
1479
1480 if (ft_section == NULL)
1481 {
1482 fprintf (file,
1483 _("\nThere is a first thunk, but the section containing it could not be found\n"));
1484 continue;
1485 }
1486
1487 /* Now check to see if this section is the same as our current
1488 section. If it is not then we will have to load its data in. */
4e1fc599 1489 if (ft_section != section)
6e7c73dd
CF
1490 {
1491 ft_idx = first_thunk - (ft_section->vma - extra->ImageBase);
4e1fc599
AM
1492 ft_datasize = ft_section->size - ft_idx;
1493 ft_data = (bfd_byte *) bfd_malloc (ft_datasize);
6e7c73dd
CF
1494 if (ft_data == NULL)
1495 continue;
1496
4e1fc599
AM
1497 /* Read ft_datasize bytes starting at offset ft_idx. */
1498 if (!bfd_get_section_contents (abfd, ft_section, ft_data,
1499 (bfd_vma) ft_idx, ft_datasize))
6e7c73dd
CF
1500 {
1501 free (ft_data);
1502 continue;
1503 }
6e7c73dd
CF
1504 ft_allocated = 1;
1505 }
1506 }
5e226794
NC
1507
1508 /* Print HintName vector entries. */
99ad8390 1509#ifdef COFF_WITH_pex64
4e1fc599 1510 for (j = 0; idx + j + 8 <= datasize; j += 8)
99ad8390 1511 {
f41e4712 1512 bfd_size_type amt;
99ad8390
NC
1513 unsigned long member = bfd_get_32 (abfd, data + idx + j);
1514 unsigned long member_high = bfd_get_32 (abfd, data + idx + j + 4);
1515
1516 if (!member && !member_high)
1517 break;
1518
f41e4712
NC
1519 amt = member - adj;
1520
5879bb8f 1521 if (HighBitSet (member_high))
99ad8390 1522 fprintf (file, "\t%lx%08lx\t %4lx%08lx <none>",
5879bb8f
NC
1523 member_high, member,
1524 WithoutHighBit (member_high), member);
20ad5e28 1525 /* PR binutils/17512: Handle corrupt PE data. */
4d465c68 1526 else if (amt >= datasize || amt + 2 >= datasize)
20ad5e28 1527 fprintf (file, _("\t<corrupt: 0x%04lx>"), member);
99ad8390
NC
1528 else
1529 {
1530 int ordinal;
1531 char *member_name;
1532
f41e4712
NC
1533 ordinal = bfd_get_16 (abfd, data + amt);
1534 member_name = (char *) data + amt + 2;
1535 fprintf (file, "\t%04lx\t %4d %.*s",member, ordinal,
1536 (int) (datasize - (amt + 2)), member_name);
99ad8390
NC
1537 }
1538
1539 /* If the time stamp is not zero, the import address
1540 table holds actual addresses. */
1541 if (time_stamp != 0
1542 && first_thunk != 0
4e1fc599
AM
1543 && first_thunk != hint_addr
1544 && j + 4 <= ft_datasize)
99ad8390 1545 fprintf (file, "\t%04lx",
4e1fc599 1546 (unsigned long) bfd_get_32 (abfd, ft_data + j));
99ad8390
NC
1547 fprintf (file, "\n");
1548 }
1549#else
4e1fc599 1550 for (j = 0; idx + j + 4 <= datasize; j += 4)
277d1b5e 1551 {
f41e4712 1552 bfd_size_type amt;
277d1b5e
ILT
1553 unsigned long member = bfd_get_32 (abfd, data + idx + j);
1554
4e1fc599 1555 /* Print single IMAGE_IMPORT_BY_NAME vector. */
277d1b5e
ILT
1556 if (member == 0)
1557 break;
5e226794 1558
f41e4712 1559 amt = member - adj;
4d465c68 1560
5879bb8f 1561 if (HighBitSet (member))
5e226794 1562 fprintf (file, "\t%04lx\t %4lu <none>",
5879bb8f 1563 member, WithoutHighBit (member));
20ad5e28 1564 /* PR binutils/17512: Handle corrupt PE data. */
4d465c68 1565 else if (amt >= datasize || amt + 2 >= datasize)
20ad5e28 1566 fprintf (file, _("\t<corrupt: 0x%04lx>"), member);
277d1b5e
ILT
1567 else
1568 {
1569 int ordinal;
1570 char *member_name;
1571
f41e4712
NC
1572 ordinal = bfd_get_16 (abfd, data + amt);
1573 member_name = (char *) data + amt + 2;
1574 fprintf (file, "\t%04lx\t %4d %.*s",
1575 member, ordinal,
1576 (int) (datasize - (amt + 2)), member_name);
277d1b5e 1577 }
5e226794 1578
277d1b5e 1579 /* If the time stamp is not zero, the import address
5e226794
NC
1580 table holds actual addresses. */
1581 if (time_stamp != 0
1582 && first_thunk != 0
4e1fc599
AM
1583 && first_thunk != hint_addr
1584 && j + 4 <= ft_datasize)
277d1b5e 1585 fprintf (file, "\t%04lx",
4e1fc599 1586 (unsigned long) bfd_get_32 (abfd, ft_data + j));
277d1b5e
ILT
1587
1588 fprintf (file, "\n");
1589 }
99ad8390 1590#endif
e4cf60a8
NC
1591 if (ft_allocated)
1592 free (ft_data);
277d1b5e
ILT
1593 }
1594
9602af51 1595 fprintf (file, "\n");
277d1b5e
ILT
1596 }
1597
1598 free (data);
1599
b34976b6 1600 return TRUE;
277d1b5e
ILT
1601}
1602
b34976b6 1603static bfd_boolean
7920ce38 1604pe_print_edata (bfd * abfd, void * vfile)
277d1b5e
ILT
1605{
1606 FILE *file = (FILE *) vfile;
a76b448c 1607 bfd_byte *data;
8181c403 1608 asection *section;
a76b448c 1609 bfd_size_type datasize = 0;
277d1b5e
ILT
1610 bfd_size_type dataoff;
1611 bfd_size_type i;
b69c8728 1612 bfd_vma adj;
1725a96e
NC
1613 struct EDT_type
1614 {
07d6d2b8 1615 long export_flags; /* Reserved - should be zero. */
6fa957a9
KH
1616 long time_stamp;
1617 short major_ver;
1618 short minor_ver;
07d6d2b8
AM
1619 bfd_vma name; /* RVA - relative to image base. */
1620 long base; /* Ordinal base. */
7920ce38 1621 unsigned long num_functions;/* Number in the export address table. */
07d6d2b8 1622 unsigned long num_names; /* Number in the name pointer table. */
7920ce38
NC
1623 bfd_vma eat_addr; /* RVA to the export address table. */
1624 bfd_vma npt_addr; /* RVA to the Export Name Pointer Table. */
1625 bfd_vma ot_addr; /* RVA to the Ordinal Table. */
6fa957a9 1626 } edt;
277d1b5e
ILT
1627
1628 pe_data_type *pe = pe_data (abfd);
1629 struct internal_extra_pe_aouthdr *extra = &pe->pe_opthdr;
1630
8181c403 1631 bfd_vma addr;
277d1b5e 1632
6c73cbb1 1633 addr = extra->DataDirectory[PE_EXPORT_TABLE].VirtualAddress;
277d1b5e 1634
6c73cbb1 1635 if (addr == 0 && extra->DataDirectory[PE_EXPORT_TABLE].Size == 0)
8181c403 1636 {
a76b448c
AM
1637 /* Maybe the extra header isn't there. Look for the section. */
1638 section = bfd_get_section_by_name (abfd, ".edata");
1639 if (section == NULL)
b34976b6 1640 return TRUE;
a76b448c
AM
1641
1642 addr = section->vma;
0facbdf5 1643 dataoff = 0;
eea6121a 1644 datasize = section->size;
a76b448c 1645 if (datasize == 0)
b34976b6 1646 return TRUE;
8181c403 1647 }
a76b448c 1648 else
8181c403 1649 {
a76b448c 1650 addr += extra->ImageBase;
1725a96e 1651
a76b448c 1652 for (section = abfd->sections; section != NULL; section = section->next)
0facbdf5
NC
1653 if (addr >= section->vma && addr < section->vma + section->size)
1654 break;
a76b448c
AM
1655
1656 if (section == NULL)
1657 {
1658 fprintf (file,
1659 _("\nThere is an export table, but the section containing it could not be found\n"));
b34976b6 1660 return TRUE;
a76b448c 1661 }
b69c8728 1662 else if (!(section->flags & SEC_HAS_CONTENTS))
07d6d2b8 1663 {
b69c8728
JT
1664 fprintf (file,
1665 _("\nThere is an export table in %s, but that section has no contents\n"),
1666 section->name);
1667 return TRUE;
07d6d2b8 1668 }
0facbdf5
NC
1669
1670 dataoff = addr - section->vma;
6c73cbb1 1671 datasize = extra->DataDirectory[PE_EXPORT_TABLE].Size;
cf93e9c2
AM
1672 if (dataoff > section->size
1673 || datasize > section->size - dataoff)
0facbdf5
NC
1674 {
1675 fprintf (file,
1676 _("\nThere is an export table in %s, but it does not fit into that section\n"),
1677 section->name);
1678 return TRUE;
1679 }
277d1b5e
ILT
1680 }
1681
5a4b0ccc 1682 /* PR 17512: Handle corrupt PE binaries. */
b4560c7d 1683 if (datasize < 40)
5a4b0ccc
NC
1684 {
1685 fprintf (file,
695344c0 1686 /* xgettext:c-format */
5a4b0ccc
NC
1687 _("\nThere is an export table in %s, but it is too small (%d)\n"),
1688 section->name, (int) datasize);
1689 return TRUE;
1690 }
1691
695344c0 1692 /* xgettext:c-format */
8181c403
AM
1693 fprintf (file, _("\nThere is an export table in %s at 0x%lx\n"),
1694 section->name, (unsigned long) addr);
1695
a50b1753 1696 data = (bfd_byte *) bfd_malloc (datasize);
8181c403 1697 if (data == NULL)
b34976b6 1698 return FALSE;
277d1b5e 1699
7920ce38 1700 if (! bfd_get_section_contents (abfd, section, data,
dc810e39 1701 (file_ptr) dataoff, datasize))
b34976b6 1702 return FALSE;
277d1b5e 1703
6fa957a9 1704 /* Go get Export Directory Table. */
07d6d2b8
AM
1705 edt.export_flags = bfd_get_32 (abfd, data + 0);
1706 edt.time_stamp = bfd_get_32 (abfd, data + 4);
1707 edt.major_ver = bfd_get_16 (abfd, data + 8);
1708 edt.minor_ver = bfd_get_16 (abfd, data + 10);
1709 edt.name = bfd_get_32 (abfd, data + 12);
1710 edt.base = bfd_get_32 (abfd, data + 16);
6fa957a9 1711 edt.num_functions = bfd_get_32 (abfd, data + 20);
07d6d2b8
AM
1712 edt.num_names = bfd_get_32 (abfd, data + 24);
1713 edt.eat_addr = bfd_get_32 (abfd, data + 28);
1714 edt.npt_addr = bfd_get_32 (abfd, data + 32);
1715 edt.ot_addr = bfd_get_32 (abfd, data + 36);
277d1b5e 1716
8181c403 1717 adj = section->vma - extra->ImageBase + dataoff;
277d1b5e 1718
1725a96e 1719 /* Dump the EDT first. */
9602af51 1720 fprintf (file,
6fa957a9
KH
1721 _("\nThe Export Tables (interpreted %s section contents)\n\n"),
1722 section->name);
277d1b5e 1723
9602af51 1724 fprintf (file,
6fa957a9 1725 _("Export Flags \t\t\t%lx\n"), (unsigned long) edt.export_flags);
277d1b5e 1726
9602af51 1727 fprintf (file,
6fa957a9 1728 _("Time/Date stamp \t\t%lx\n"), (unsigned long) edt.time_stamp);
277d1b5e 1729
9602af51 1730 fprintf (file,
695344c0 1731 /* xgettext:c-format */
6fa957a9 1732 _("Major/Minor \t\t\t%d/%d\n"), edt.major_ver, edt.minor_ver);
277d1b5e
ILT
1733
1734 fprintf (file,
1735 _("Name \t\t\t\t"));
ebf12fbe 1736 bfd_fprintf_vma (abfd, file, edt.name);
b69c8728
JT
1737
1738 if ((edt.name >= adj) && (edt.name < adj + datasize))
201159ec
NC
1739 fprintf (file, " %.*s\n",
1740 (int) (datasize - (edt.name - adj)),
1741 data + edt.name - adj);
b69c8728
JT
1742 else
1743 fprintf (file, "(outside .edata section)\n");
277d1b5e 1744
9602af51 1745 fprintf (file,
6fa957a9 1746 _("Ordinal Base \t\t\t%ld\n"), edt.base);
277d1b5e 1747
9602af51 1748 fprintf (file,
6fa957a9 1749 _("Number in:\n"));
277d1b5e 1750
9602af51 1751 fprintf (file,
6fa957a9
KH
1752 _("\tExport Address Table \t\t%08lx\n"),
1753 edt.num_functions);
277d1b5e 1754
9602af51 1755 fprintf (file,
6fa957a9 1756 _("\t[Name Pointer/Ordinal] Table\t%08lx\n"), edt.num_names);
277d1b5e 1757
9602af51 1758 fprintf (file,
6fa957a9 1759 _("Table Addresses\n"));
277d1b5e
ILT
1760
1761 fprintf (file,
1762 _("\tExport Address Table \t\t"));
ebf12fbe 1763 bfd_fprintf_vma (abfd, file, edt.eat_addr);
277d1b5e
ILT
1764 fprintf (file, "\n");
1765
1766 fprintf (file,
6fa957a9 1767 _("\tName Pointer Table \t\t"));
ebf12fbe 1768 bfd_fprintf_vma (abfd, file, edt.npt_addr);
277d1b5e
ILT
1769 fprintf (file, "\n");
1770
1771 fprintf (file,
1772 _("\tOrdinal Table \t\t\t"));
ebf12fbe 1773 bfd_fprintf_vma (abfd, file, edt.ot_addr);
277d1b5e
ILT
1774 fprintf (file, "\n");
1775
5933bdc9 1776 /* The next table to find is the Export Address Table. It's basically
277d1b5e
ILT
1777 a list of pointers that either locate a function in this dll, or
1778 forward the call to another dll. Something like:
1725a96e
NC
1779 typedef union
1780 {
07d6d2b8
AM
1781 long export_rva;
1782 long forwarder_rva;
7920ce38 1783 } export_address_table_entry; */
277d1b5e 1784
9602af51 1785 fprintf (file,
277d1b5e
ILT
1786 _("\nExport Address Table -- Ordinal Base %ld\n"),
1787 edt.base);
1788
bf67003b 1789 /* PR 17512: Handle corrupt PE binaries. */
cf93e9c2
AM
1790 /* PR 17512 file: 140-165018-0.004. */
1791 if (edt.eat_addr - adj >= datasize
64d29018 1792 /* PR 17512: file: 092b1829 */
cf93e9c2
AM
1793 || (edt.num_functions + 1) * 4 < edt.num_functions
1794 || edt.eat_addr - adj + (edt.num_functions + 1) * 4 > datasize)
bf67003b
NC
1795 fprintf (file, _("\tInvalid Export Address Table rva (0x%lx) or entry count (0x%lx)\n"),
1796 (long) edt.eat_addr,
1797 (long) edt.num_functions);
1798 else for (i = 0; i < edt.num_functions; ++i)
277d1b5e
ILT
1799 {
1800 bfd_vma eat_member = bfd_get_32 (abfd,
8181c403 1801 data + edt.eat_addr + (i * 4) - adj);
277d1b5e
ILT
1802 if (eat_member == 0)
1803 continue;
1804
db8503c4 1805 if (eat_member - adj <= datasize)
277d1b5e 1806 {
db8503c4 1807 /* This rva is to a name (forwarding function) in our section. */
6fa957a9 1808 /* Should locate a function descriptor. */
5933bdc9 1809 fprintf (file,
36e9d67b 1810 "\t[%4ld] +base[%4ld] %04lx %s -- %.*s\n",
a76b448c
AM
1811 (long) i,
1812 (long) (i + edt.base),
1813 (unsigned long) eat_member,
1814 _("Forwarder RVA"),
36e9d67b 1815 (int)(datasize - (eat_member - adj)),
a76b448c 1816 data + eat_member - adj);
277d1b5e
ILT
1817 }
1818 else
1819 {
6fa957a9 1820 /* Should locate a function descriptor in the reldata section. */
5933bdc9
ILT
1821 fprintf (file,
1822 "\t[%4ld] +base[%4ld] %04lx %s\n",
a76b448c
AM
1823 (long) i,
1824 (long) (i + edt.base),
1825 (unsigned long) eat_member,
5933bdc9 1826 _("Export RVA"));
277d1b5e
ILT
1827 }
1828 }
1829
6fa957a9
KH
1830 /* The Export Name Pointer Table is paired with the Export Ordinal Table. */
1831 /* Dump them in parallel for clarity. */
9602af51 1832 fprintf (file,
6fa957a9 1833 _("\n[Ordinal/Name Pointer] Table\n"));
277d1b5e 1834
bf67003b 1835 /* PR 17512: Handle corrupt PE binaries. */
36e9d67b 1836 if (edt.npt_addr + (edt.num_names * 4) - adj >= datasize
64d29018
NC
1837 /* PR 17512: file: bb68816e. */
1838 || edt.num_names * 4 < edt.num_names
36e9d67b 1839 || (data + edt.npt_addr - adj) < data)
695344c0 1840 /* xgettext:c-format */
bf67003b
NC
1841 fprintf (file, _("\tInvalid Name Pointer Table rva (0x%lx) or entry count (0x%lx)\n"),
1842 (long) edt.npt_addr,
1843 (long) edt.num_names);
36e9d67b
NC
1844 /* PR 17512: file: 140-147171-0.004. */
1845 else if (edt.ot_addr + (edt.num_names * 2) - adj >= datasize
1846 || data + edt.ot_addr - adj < data)
695344c0 1847 /* xgettext:c-format */
bf67003b
NC
1848 fprintf (file, _("\tInvalid Ordinal Table rva (0x%lx) or entry count (0x%lx)\n"),
1849 (long) edt.ot_addr,
1850 (long) edt.num_names);
1851 else for (i = 0; i < edt.num_names; ++i)
277d1b5e 1852 {
20ad5e28
NC
1853 bfd_vma name_ptr;
1854 bfd_vma ord;
9602af51 1855
20ad5e28
NC
1856 ord = bfd_get_16 (abfd, data + edt.ot_addr + (i * 2) - adj);
1857 name_ptr = bfd_get_32 (abfd, data + edt.npt_addr + (i * 4) - adj);
277d1b5e 1858
20ad5e28
NC
1859 if ((name_ptr - adj) >= datasize)
1860 {
695344c0 1861 /* xgettext:c-format */
20ad5e28
NC
1862 fprintf (file, _("\t[%4ld] <corrupt offset: %lx>\n"),
1863 (long) ord, (long) name_ptr);
1864 }
1865 else
1866 {
1867 char * name = (char *) data + name_ptr - adj;
1868
36e9d67b
NC
1869 fprintf (file, "\t[%4ld] %.*s\n", (long) ord,
1870 (int)((char *)(data + datasize) - name), name);
20ad5e28 1871 }
277d1b5e
ILT
1872 }
1873
1874 free (data);
1875
b34976b6 1876 return TRUE;
277d1b5e
ILT
1877}
1878
fac41780
JW
1879/* This really is architecture dependent. On IA-64, a .pdata entry
1880 consists of three dwords containing relative virtual addresses that
1881 specify the start and end address of the code range the entry
4e1fc599 1882 covers and the address of the corresponding unwind info data.
2b5c217d
NC
1883
1884 On ARM and SH-4, a compressed PDATA structure is used :
1885 _IMAGE_CE_RUNTIME_FUNCTION_ENTRY, whereas MIPS is documented to use
1886 _IMAGE_ALPHA_RUNTIME_FUNCTION_ENTRY.
1887 See http://msdn2.microsoft.com/en-us/library/ms253988(VS.80).aspx .
1888
799c00e0 1889 This is the version for uncompressed data. */
6fa957a9 1890
b34976b6 1891static bfd_boolean
7920ce38 1892pe_print_pdata (bfd * abfd, void * vfile)
277d1b5e 1893{
99ad8390
NC
1894#if defined(COFF_WITH_pep) && !defined(COFF_WITH_pex64)
1895# define PDATA_ROW_SIZE (3 * 8)
fac41780 1896#else
99ad8390 1897# define PDATA_ROW_SIZE (5 * 4)
fac41780 1898#endif
277d1b5e
ILT
1899 FILE *file = (FILE *) vfile;
1900 bfd_byte *data = 0;
1901 asection *section = bfd_get_section_by_name (abfd, ".pdata");
1902 bfd_size_type datasize = 0;
1903 bfd_size_type i;
1904 bfd_size_type start, stop;
fac41780 1905 int onaline = PDATA_ROW_SIZE;
277d1b5e 1906
5933bdc9
ILT
1907 if (section == NULL
1908 || coff_section_data (abfd, section) == NULL
1909 || pei_section_data (abfd, section) == NULL)
b34976b6 1910 return TRUE;
277d1b5e 1911
5933bdc9 1912 stop = pei_section_data (abfd, section)->virt_size;
277d1b5e 1913 if ((stop % onaline) != 0)
6fa957a9 1914 fprintf (file,
695344c0 1915 /* xgettext:c-format */
59d08d6c 1916 _("warning, .pdata section size (%ld) is not a multiple of %d\n"),
6fa957a9 1917 (long) stop, onaline);
277d1b5e 1918
5933bdc9
ILT
1919 fprintf (file,
1920 _("\nThe Function Table (interpreted .pdata section contents)\n"));
99ad8390 1921#if defined(COFF_WITH_pep) && !defined(COFF_WITH_pex64)
9602af51 1922 fprintf (file,
6fa957a9 1923 _(" vma:\t\t\tBegin Address End Address Unwind Info\n"));
fac41780 1924#else
ca09e32b
NC
1925 fprintf (file, _("\
1926 vma:\t\tBegin End EH EH PrologEnd Exception\n\
1927 \t\tAddress Address Handler Data Address Mask\n"));
fac41780 1928#endif
277d1b5e 1929
eea6121a 1930 datasize = section->size;
dc810e39 1931 if (datasize == 0)
b34976b6 1932 return TRUE;
277d1b5e 1933
6937bb54
NC
1934 /* PR 17512: file: 002-193900-0.004. */
1935 if (datasize < stop)
1936 {
695344c0 1937 /* xgettext:c-format */
6937bb54
NC
1938 fprintf (file, _("Virtual size of .pdata section (%ld) larger than real size (%ld)\n"),
1939 (long) stop, (long) datasize);
1940 return FALSE;
1941 }
1942
7920ce38 1943 if (! bfd_malloc_and_get_section (abfd, section, &data))
eea6121a
AM
1944 {
1945 if (data != NULL)
1946 free (data);
1947 return FALSE;
1948 }
277d1b5e
ILT
1949
1950 start = 0;
1951
1952 for (i = start; i < stop; i += onaline)
1953 {
1954 bfd_vma begin_addr;
1955 bfd_vma end_addr;
1956 bfd_vma eh_handler;
1957 bfd_vma eh_data;
1958 bfd_vma prolog_end_addr;
c7e2358a 1959#if !defined(COFF_WITH_pep) || defined(COFF_WITH_pex64)
5933bdc9 1960 int em_data;
c7e2358a 1961#endif
277d1b5e 1962
fac41780 1963 if (i + PDATA_ROW_SIZE > stop)
277d1b5e 1964 break;
5933bdc9 1965
07d6d2b8
AM
1966 begin_addr = GET_PDATA_ENTRY (abfd, data + i );
1967 end_addr = GET_PDATA_ENTRY (abfd, data + i + 4);
6fa957a9 1968 eh_handler = GET_PDATA_ENTRY (abfd, data + i + 8);
07d6d2b8 1969 eh_data = GET_PDATA_ENTRY (abfd, data + i + 12);
6fa957a9 1970 prolog_end_addr = GET_PDATA_ENTRY (abfd, data + i + 16);
9602af51 1971
277d1b5e
ILT
1972 if (begin_addr == 0 && end_addr == 0 && eh_handler == 0
1973 && eh_data == 0 && prolog_end_addr == 0)
1725a96e
NC
1974 /* We are probably into the padding of the section now. */
1975 break;
277d1b5e 1976
c7e2358a 1977#if !defined(COFF_WITH_pep) || defined(COFF_WITH_pex64)
5933bdc9 1978 em_data = ((eh_handler & 0x1) << 2) | (prolog_end_addr & 0x3);
c7e2358a 1979#endif
6fa957a9
KH
1980 eh_handler &= ~(bfd_vma) 0x3;
1981 prolog_end_addr &= ~(bfd_vma) 0x3;
fac41780
JW
1982
1983 fputc (' ', file);
ebf12fbe
DK
1984 bfd_fprintf_vma (abfd, file, i + section->vma); fputc ('\t', file);
1985 bfd_fprintf_vma (abfd, file, begin_addr); fputc (' ', file);
1986 bfd_fprintf_vma (abfd, file, end_addr); fputc (' ', file);
1987 bfd_fprintf_vma (abfd, file, eh_handler);
99ad8390 1988#if !defined(COFF_WITH_pep) || defined(COFF_WITH_pex64)
fac41780 1989 fputc (' ', file);
ebf12fbe
DK
1990 bfd_fprintf_vma (abfd, file, eh_data); fputc (' ', file);
1991 bfd_fprintf_vma (abfd, file, prolog_end_addr);
fac41780
JW
1992 fprintf (file, " %x", em_data);
1993#endif
277d1b5e
ILT
1994
1995#ifdef POWERPC_LE_PE
1996 if (eh_handler == 0 && eh_data != 0)
1997 {
6fa957a9 1998 /* Special bits here, although the meaning may be a little
7920ce38
NC
1999 mysterious. The only one I know for sure is 0x03
2000 Code Significance
2001 0x00 None
2002 0x01 Register Save Millicode
2003 0x02 Register Restore Millicode
2004 0x03 Glue Code Sequence. */
277d1b5e
ILT
2005 switch (eh_data)
2006 {
2007 case 0x01:
9602af51 2008 fprintf (file, _(" Register save millicode"));
277d1b5e
ILT
2009 break;
2010 case 0x02:
9602af51 2011 fprintf (file, _(" Register restore millicode"));
277d1b5e
ILT
2012 break;
2013 case 0x03:
9602af51 2014 fprintf (file, _(" Glue code sequence"));
277d1b5e
ILT
2015 break;
2016 default:
2017 break;
2018 }
2019 }
2020#endif
9602af51 2021 fprintf (file, "\n");
277d1b5e
ILT
2022 }
2023
2024 free (data);
2025
b34976b6 2026 return TRUE;
2b5c217d 2027#undef PDATA_ROW_SIZE
277d1b5e
ILT
2028}
2029
799c00e0
NC
2030typedef struct sym_cache
2031{
07d6d2b8 2032 int symcount;
799c00e0
NC
2033 asymbol ** syms;
2034} sym_cache;
2035
2036static asymbol **
2037slurp_symtab (bfd *abfd, sym_cache *psc)
2038{
2039 asymbol ** sy = NULL;
2040 long storage;
2041
2042 if (!(bfd_get_file_flags (abfd) & HAS_SYMS))
2043 {
2044 psc->symcount = 0;
2045 return NULL;
2046 }
2047
2048 storage = bfd_get_symtab_upper_bound (abfd);
2049 if (storage < 0)
2050 return NULL;
2051 if (storage)
86eafac0
NC
2052 {
2053 sy = (asymbol **) bfd_malloc (storage);
2054 if (sy == NULL)
2055 return NULL;
2056 }
799c00e0
NC
2057
2058 psc->symcount = bfd_canonicalize_symtab (abfd, sy);
2059 if (psc->symcount < 0)
2060 return NULL;
2061 return sy;
2062}
2063
2064static const char *
2065my_symbol_for_address (bfd *abfd, bfd_vma func, sym_cache *psc)
2066{
2067 int i;
2068
2069 if (psc->syms == 0)
2070 psc->syms = slurp_symtab (abfd, psc);
2071
2072 for (i = 0; i < psc->symcount; i++)
2073 {
2074 if (psc->syms[i]->section->vma + psc->syms[i]->value == func)
2075 return psc->syms[i]->name;
2076 }
2077
2078 return NULL;
2079}
2080
2081static void
2082cleanup_syms (sym_cache *psc)
2083{
2084 psc->symcount = 0;
2085 free (psc->syms);
2086 psc->syms = NULL;
2087}
2088
2089/* This is the version for "compressed" pdata. */
2090
2091bfd_boolean
2092_bfd_XX_print_ce_compressed_pdata (bfd * abfd, void * vfile)
2093{
2094# define PDATA_ROW_SIZE (2 * 4)
2095 FILE *file = (FILE *) vfile;
2096 bfd_byte *data = NULL;
2097 asection *section = bfd_get_section_by_name (abfd, ".pdata");
2098 bfd_size_type datasize = 0;
2099 bfd_size_type i;
2100 bfd_size_type start, stop;
2101 int onaline = PDATA_ROW_SIZE;
91d6fa6a 2102 struct sym_cache cache = {0, 0} ;
799c00e0
NC
2103
2104 if (section == NULL
2105 || coff_section_data (abfd, section) == NULL
2106 || pei_section_data (abfd, section) == NULL)
2107 return TRUE;
2108
2109 stop = pei_section_data (abfd, section)->virt_size;
2110 if ((stop % onaline) != 0)
2111 fprintf (file,
695344c0 2112 /* xgettext:c-format */
59d08d6c 2113 _("warning, .pdata section size (%ld) is not a multiple of %d\n"),
799c00e0
NC
2114 (long) stop, onaline);
2115
2116 fprintf (file,
2117 _("\nThe Function Table (interpreted .pdata section contents)\n"));
2118
2119 fprintf (file, _("\
2120 vma:\t\tBegin Prolog Function Flags Exception EH\n\
2121 \t\tAddress Length Length 32b exc Handler Data\n"));
2122
2123 datasize = section->size;
2124 if (datasize == 0)
2125 return TRUE;
2126
2127 if (! bfd_malloc_and_get_section (abfd, section, &data))
2128 {
2129 if (data != NULL)
2130 free (data);
2131 return FALSE;
2132 }
2133
2134 start = 0;
2135
2136 for (i = start; i < stop; i += onaline)
2137 {
2138 bfd_vma begin_addr;
2139 bfd_vma other_data;
2140 bfd_vma prolog_length, function_length;
2141 int flag32bit, exception_flag;
799c00e0
NC
2142 asection *tsection;
2143
2144 if (i + PDATA_ROW_SIZE > stop)
2145 break;
2146
2147 begin_addr = GET_PDATA_ENTRY (abfd, data + i );
2148 other_data = GET_PDATA_ENTRY (abfd, data + i + 4);
2149
2150 if (begin_addr == 0 && other_data == 0)
2151 /* We are probably into the padding of the section now. */
2152 break;
2153
2154 prolog_length = (other_data & 0x000000FF);
2155 function_length = (other_data & 0x3FFFFF00) >> 8;
2156 flag32bit = (int)((other_data & 0x40000000) >> 30);
2157 exception_flag = (int)((other_data & 0x80000000) >> 31);
2158
2159 fputc (' ', file);
ebf12fbe
DK
2160 bfd_fprintf_vma (abfd, file, i + section->vma); fputc ('\t', file);
2161 bfd_fprintf_vma (abfd, file, begin_addr); fputc (' ', file);
2162 bfd_fprintf_vma (abfd, file, prolog_length); fputc (' ', file);
2163 bfd_fprintf_vma (abfd, file, function_length); fputc (' ', file);
799c00e0
NC
2164 fprintf (file, "%2d %2d ", flag32bit, exception_flag);
2165
2166 /* Get the exception handler's address and the data passed from the
07d6d2b8
AM
2167 .text section. This is really the data that belongs with the .pdata
2168 but got "compressed" out for the ARM and SH4 architectures. */
799c00e0
NC
2169 tsection = bfd_get_section_by_name (abfd, ".text");
2170 if (tsection && coff_section_data (abfd, tsection)
2171 && pei_section_data (abfd, tsection))
2172 {
4e1fc599
AM
2173 bfd_vma eh_off = (begin_addr - 8) - tsection->vma;
2174 bfd_byte *tdata;
799c00e0 2175
4e1fc599
AM
2176 tdata = (bfd_byte *) bfd_malloc (8);
2177 if (tdata)
2178 {
2179 if (bfd_get_section_contents (abfd, tsection, tdata, eh_off, 8))
799c00e0
NC
2180 {
2181 bfd_vma eh, eh_data;
2182
2183 eh = bfd_get_32 (abfd, tdata);
2184 eh_data = bfd_get_32 (abfd, tdata + 4);
2185 fprintf (file, "%08x ", (unsigned int) eh);
2186 fprintf (file, "%08x", (unsigned int) eh_data);
2187 if (eh != 0)
2188 {
91d6fa6a 2189 const char *s = my_symbol_for_address (abfd, eh, &cache);
799c00e0
NC
2190
2191 if (s)
2192 fprintf (file, " (%s) ", s);
2193 }
2194 }
2195 free (tdata);
2196 }
799c00e0
NC
2197 }
2198
2199 fprintf (file, "\n");
2200 }
2201
2202 free (data);
2203
91d6fa6a 2204 cleanup_syms (& cache);
799c00e0
NC
2205
2206 return TRUE;
2207#undef PDATA_ROW_SIZE
2208}
c7c7219d 2209
799c00e0 2210\f
5933bdc9 2211#define IMAGE_REL_BASED_HIGHADJ 4
1725a96e 2212static const char * const tbl[] =
7920ce38
NC
2213{
2214 "ABSOLUTE",
2215 "HIGH",
2216 "LOW",
2217 "HIGHLOW",
2218 "HIGHADJ",
2219 "MIPS_JMPADDR",
2220 "SECTION",
2221 "REL32",
2222 "RESERVED1",
2223 "MIPS_JMPADDR16",
2224 "DIR64",
2bfd55ca 2225 "HIGH3ADJ",
7920ce38
NC
2226 "UNKNOWN", /* MUST be last. */
2227};
277d1b5e 2228
b34976b6 2229static bfd_boolean
7920ce38 2230pe_print_reloc (bfd * abfd, void * vfile)
277d1b5e
ILT
2231{
2232 FILE *file = (FILE *) vfile;
2233 bfd_byte *data = 0;
2234 asection *section = bfd_get_section_by_name (abfd, ".reloc");
513ea82e 2235 bfd_byte *p, *end;
277d1b5e 2236
b69c8728 2237 if (section == NULL || section->size == 0 || !(section->flags & SEC_HAS_CONTENTS))
b34976b6 2238 return TRUE;
277d1b5e 2239
5933bdc9
ILT
2240 fprintf (file,
2241 _("\n\nPE File Base Relocations (interpreted .reloc section contents)\n"));
277d1b5e 2242
7920ce38 2243 if (! bfd_malloc_and_get_section (abfd, section, &data))
eea6121a
AM
2244 {
2245 if (data != NULL)
2246 free (data);
2247 return FALSE;
2248 }
277d1b5e 2249
513ea82e
AM
2250 p = data;
2251 end = data + section->size;
2252 while (p + 8 <= end)
277d1b5e
ILT
2253 {
2254 int j;
2255 bfd_vma virtual_address;
77ef8654 2256 unsigned long number, size;
513ea82e 2257 bfd_byte *chunk_end;
277d1b5e
ILT
2258
2259 /* The .reloc section is a sequence of blocks, with a header consisting
1725a96e 2260 of two 32 bit quantities, followed by a number of 16 bit entries. */
513ea82e
AM
2261 virtual_address = bfd_get_32 (abfd, p);
2262 size = bfd_get_32 (abfd, p + 4);
2263 p += 8;
277d1b5e
ILT
2264 number = (size - 8) / 2;
2265
2266 if (size == 0)
1725a96e 2267 break;
277d1b5e
ILT
2268
2269 fprintf (file,
695344c0 2270 /* xgettext:c-format */
277d1b5e 2271 _("\nVirtual Address: %08lx Chunk size %ld (0x%lx) Number of fixups %ld\n"),
77ef8654 2272 (unsigned long) virtual_address, size, size, number);
277d1b5e 2273
10169134 2274 chunk_end = p - 8 + size;
513ea82e
AM
2275 if (chunk_end > end)
2276 chunk_end = end;
2277 j = 0;
2278 while (p + 2 <= chunk_end)
277d1b5e 2279 {
513ea82e 2280 unsigned short e = bfd_get_16 (abfd, p);
5933bdc9 2281 unsigned int t = (e & 0xF000) >> 12;
277d1b5e
ILT
2282 int off = e & 0x0FFF;
2283
5933bdc9
ILT
2284 if (t >= sizeof (tbl) / sizeof (tbl[0]))
2285 t = (sizeof (tbl) / sizeof (tbl[0])) - 1;
277d1b5e 2286
5933bdc9 2287 fprintf (file,
695344c0 2288 /* xgettext:c-format */
5933bdc9 2289 _("\treloc %4d offset %4x [%4lx] %s"),
0af1713e 2290 j, off, (unsigned long) (off + virtual_address), tbl[t]);
277d1b5e 2291
513ea82e
AM
2292 p += 2;
2293 j++;
2294
17505c5c 2295 /* HIGHADJ takes an argument, - the next record *is* the
9602af51 2296 low 16 bits of addend. */
513ea82e 2297 if (t == IMAGE_REL_BASED_HIGHADJ && p + 2 <= chunk_end)
5933bdc9 2298 {
513ea82e
AM
2299 fprintf (file, " (%4x)", (unsigned int) bfd_get_16 (abfd, p));
2300 p += 2;
6fa957a9 2301 j++;
5933bdc9 2302 }
9602af51 2303
17505c5c 2304 fprintf (file, "\n");
277d1b5e 2305 }
277d1b5e
ILT
2306 }
2307
2308 free (data);
2309
b34976b6 2310 return TRUE;
277d1b5e 2311}
5879bb8f 2312\f
3714081c
NC
2313/* A data structure describing the regions of a .rsrc section.
2314 Some fields are filled in as the section is parsed. */
2315
2316typedef struct rsrc_regions
2317{
2318 bfd_byte * section_start;
2319 bfd_byte * section_end;
2320 bfd_byte * strings_start;
2321 bfd_byte * resource_start;
2322} rsrc_regions;
277d1b5e 2323
11a6da56 2324static bfd_byte *
3714081c
NC
2325rsrc_print_resource_directory (FILE * , bfd *, unsigned int, bfd_byte *,
2326 rsrc_regions *, bfd_vma);
11a6da56 2327
20ad5e28
NC
2328/* Print the resource entry at DATA, with the text indented by INDENT.
2329 Recusively calls rsrc_print_resource_directory to print the contents
2330 of directory entries.
2331 Returns the address of the end of the data associated with the entry
2332 or section_end + 1 upon failure. */
2333
11a6da56 2334static bfd_byte *
07d6d2b8
AM
2335rsrc_print_resource_entries (FILE * file,
2336 bfd * abfd,
3714081c
NC
2337 unsigned int indent,
2338 bfd_boolean is_name,
07d6d2b8 2339 bfd_byte * data,
3714081c 2340 rsrc_regions * regions,
07d6d2b8 2341 bfd_vma rva_bias)
11a6da56
NC
2342{
2343 unsigned long entry, addr, size;
5929c344 2344 bfd_byte * leaf;
11a6da56 2345
3714081c
NC
2346 if (data + 8 >= regions->section_end)
2347 return regions->section_end + 1;
11a6da56 2348
695344c0 2349 /* xgettext:c-format */
3714081c 2350 fprintf (file, _("%03x %*.s Entry: "), (int)(data - regions->section_start), indent, " ");
11a6da56 2351
20ad5e28 2352 entry = (unsigned long) bfd_get_32 (abfd, data);
11a6da56
NC
2353 if (is_name)
2354 {
5879bb8f
NC
2355 bfd_byte * name;
2356
3714081c 2357 /* Note - the documentation says that this field is an RVA value
5879bb8f
NC
2358 but windres appears to produce a section relative offset with
2359 the top bit set. Support both styles for now. */
2360 if (HighBitSet (entry))
3714081c 2361 name = regions->section_start + WithoutHighBit (entry);
5879bb8f 2362 else
3714081c 2363 name = regions->section_start + entry - rva_bias;
5879bb8f 2364
20ad5e28 2365 if (name + 2 < regions->section_end && name > regions->section_start)
11a6da56
NC
2366 {
2367 unsigned int len;
3714081c
NC
2368
2369 if (regions->strings_start == NULL)
2370 regions->strings_start = name;
2371
5879bb8f 2372 len = bfd_get_16 (abfd, name);
9373215c 2373
5879bb8f 2374 fprintf (file, _("name: [val: %08lx len %d]: "), entry, len);
20ad5e28 2375
3714081c 2376 if (name + 2 + len * 2 < regions->section_end)
5879bb8f
NC
2377 {
2378 /* This strange loop is to cope with multibyte characters. */
2379 while (len --)
2380 {
20ad5e28
NC
2381 char c;
2382
5879bb8f 2383 name += 2;
20ad5e28
NC
2384 c = * name;
2385 /* Avoid printing control characters. */
2386 if (c > 0 && c < 32)
2387 fprintf (file, "^%c", c + 64);
2388 else
2389 fprintf (file, "%.1s", name);
5879bb8f
NC
2390 }
2391 }
11a6da56 2392 else
20ad5e28
NC
2393 {
2394 fprintf (file, _("<corrupt string length: %#x>\n"), len);
2395 /* PR binutils/17512: Do not try to continue decoding a
2396 corrupted resource section. It is likely to end up with
2397 reams of extraneous output. FIXME: We could probably
2398 continue if we disable the printing of strings... */
2399 return regions->section_end + 1;
2400 }
11a6da56
NC
2401 }
2402 else
20ad5e28
NC
2403 {
2404 fprintf (file, _("<corrupt string offset: %#lx>\n"), entry);
2405 return regions->section_end + 1;
2406 }
11a6da56
NC
2407 }
2408 else
2409 fprintf (file, _("ID: %#08lx"), entry);
9373215c 2410
11a6da56 2411 entry = (long) bfd_get_32 (abfd, data + 4);
5879bb8f 2412 fprintf (file, _(", Value: %#08lx\n"), entry);
11a6da56 2413
5879bb8f 2414 if (HighBitSet (entry))
20ad5e28
NC
2415 {
2416 data = regions->section_start + WithoutHighBit (entry);
2417 if (data <= regions->section_start || data > regions->section_end)
2418 return regions->section_end + 1;
2419
2420 /* FIXME: PR binutils/17512: A corrupt file could contain a loop
2421 in the resource table. We need some way to detect this. */
2422 return rsrc_print_resource_directory (file, abfd, indent + 1, data,
2423 regions, rva_bias);
2424 }
11a6da56 2425
5929c344
NC
2426 leaf = regions->section_start + entry;
2427
2428 if (leaf + 16 >= regions->section_end
2429 /* PR 17512: file: 055dff7e. */
2430 || leaf < regions->section_start)
3714081c 2431 return regions->section_end + 1;
11a6da56 2432
695344c0 2433 /* xgettext:c-format */
3714081c 2434 fprintf (file, _("%03x %*.s Leaf: Addr: %#08lx, Size: %#08lx, Codepage: %d\n"),
5929c344
NC
2435 (int) (entry), indent, " ",
2436 addr = (long) bfd_get_32 (abfd, leaf),
2437 size = (long) bfd_get_32 (abfd, leaf + 4),
2438 (int) bfd_get_32 (abfd, leaf + 8));
9373215c 2439
11a6da56 2440 /* Check that the reserved entry is 0. */
5929c344 2441 if (bfd_get_32 (abfd, leaf + 12) != 0
11a6da56 2442 /* And that the data address/size is valid too. */
3714081c
NC
2443 || (regions->section_start + (addr - rva_bias) + size > regions->section_end))
2444 return regions->section_end + 1;
11a6da56 2445
3714081c
NC
2446 if (regions->resource_start == NULL)
2447 regions->resource_start = regions->section_start + (addr - rva_bias);
2448
2449 return regions->section_start + (addr - rva_bias) + size;
11a6da56
NC
2450}
2451
5879bb8f
NC
2452#define max(a,b) ((a) > (b) ? (a) : (b))
2453#define min(a,b) ((a) < (b) ? (a) : (b))
2454
11a6da56 2455static bfd_byte *
07d6d2b8
AM
2456rsrc_print_resource_directory (FILE * file,
2457 bfd * abfd,
3714081c
NC
2458 unsigned int indent,
2459 bfd_byte * data,
2460 rsrc_regions * regions,
07d6d2b8 2461 bfd_vma rva_bias)
11a6da56
NC
2462{
2463 unsigned int num_names, num_ids;
5879bb8f 2464 bfd_byte * highest_data = data;
11a6da56 2465
3714081c
NC
2466 if (data + 16 >= regions->section_end)
2467 return regions->section_end + 1;
11a6da56 2468
3714081c 2469 fprintf (file, "%03x %*.s ", (int)(data - regions->section_start), indent, " ");
11a6da56
NC
2470 switch (indent)
2471 {
2472 case 0: fprintf (file, "Type"); break;
2473 case 2: fprintf (file, "Name"); break;
2474 case 4: fprintf (file, "Language"); break;
20ad5e28
NC
2475 default:
2476 fprintf (file, _("<unknown directory type: %d>\n"), indent);
2477 /* FIXME: For now we end the printing here. If in the
2478 future more directory types are added to the RSRC spec
2479 then we will need to change this. */
2480 return regions->section_end + 1;
11a6da56
NC
2481 }
2482
695344c0 2483 /* xgettext:c-format */
11a6da56
NC
2484 fprintf (file, _(" Table: Char: %d, Time: %08lx, Ver: %d/%d, Num Names: %d, IDs: %d\n"),
2485 (int) bfd_get_32 (abfd, data),
2486 (long) bfd_get_32 (abfd, data + 4),
2487 (int) bfd_get_16 (abfd, data + 8),
2488 (int) bfd_get_16 (abfd, data + 10),
2489 num_names = (int) bfd_get_16 (abfd, data + 12),
2490 num_ids = (int) bfd_get_16 (abfd, data + 14));
2491 data += 16;
2492
5879bb8f 2493 while (num_names --)
11a6da56 2494 {
5879bb8f
NC
2495 bfd_byte * entry_end;
2496
2497 entry_end = rsrc_print_resource_entries (file, abfd, indent + 1, TRUE,
3714081c 2498 data, regions, rva_bias);
5879bb8f
NC
2499 data += 8;
2500 highest_data = max (highest_data, entry_end);
3714081c 2501 if (entry_end >= regions->section_end)
5879bb8f 2502 return entry_end;
11a6da56
NC
2503 }
2504
5879bb8f 2505 while (num_ids --)
11a6da56 2506 {
5879bb8f
NC
2507 bfd_byte * entry_end;
2508
2509 entry_end = rsrc_print_resource_entries (file, abfd, indent + 1, FALSE,
3714081c 2510 data, regions, rva_bias);
5879bb8f
NC
2511 data += 8;
2512 highest_data = max (highest_data, entry_end);
3714081c 2513 if (entry_end >= regions->section_end)
5879bb8f 2514 return entry_end;
11a6da56
NC
2515 }
2516
5879bb8f 2517 return max (highest_data, data);
11a6da56
NC
2518}
2519
2520/* Display the contents of a .rsrc section. We do not try to
2521 reproduce the resources, windres does that. Instead we dump
2522 the tables in a human readable format. */
2523
2524static bfd_boolean
5879bb8f 2525rsrc_print_section (bfd * abfd, void * vfile)
11a6da56
NC
2526{
2527 bfd_vma rva_bias;
2528 pe_data_type * pe;
2529 FILE * file = (FILE *) vfile;
2530 bfd_size_type datasize;
2531 asection * section;
2532 bfd_byte * data;
3714081c 2533 rsrc_regions regions;
11a6da56 2534
11a6da56 2535 pe = pe_data (abfd);
5879bb8f 2536 if (pe == NULL)
11a6da56
NC
2537 return TRUE;
2538
5879bb8f
NC
2539 section = bfd_get_section_by_name (abfd, ".rsrc");
2540 if (section == NULL)
11a6da56 2541 return TRUE;
b69c8728
JT
2542 if (!(section->flags & SEC_HAS_CONTENTS))
2543 return TRUE;
5879bb8f 2544
11a6da56
NC
2545 datasize = section->size;
2546 if (datasize == 0)
2547 return TRUE;
2548
b69c8728
JT
2549 rva_bias = section->vma - pe->pe_opthdr.ImageBase;
2550
5879bb8f 2551 if (! bfd_malloc_and_get_section (abfd, section, & data))
11a6da56
NC
2552 {
2553 if (data != NULL)
2554 free (data);
2555 return FALSE;
2556 }
3714081c
NC
2557
2558 regions.section_start = data;
2559 regions.section_end = data + datasize;
2560 regions.strings_start = NULL;
2561 regions.resource_start = NULL;
11a6da56
NC
2562
2563 fflush (file);
2564 fprintf (file, "\nThe .rsrc Resource Directory section:\n");
2565
3714081c 2566 while (data < regions.section_end)
11a6da56 2567 {
5879bb8f
NC
2568 bfd_byte * p = data;
2569
3714081c 2570 data = rsrc_print_resource_directory (file, abfd, 0, data, & regions, rva_bias);
11a6da56 2571
3714081c 2572 if (data == regions.section_end + 1)
11a6da56
NC
2573 fprintf (file, _("Corrupt .rsrc section detected!\n"));
2574 else
2575 {
2576 /* Align data before continuing. */
2577 int align = (1 << section->alignment_power) - 1;
5879bb8f 2578
b9e95fa2 2579 data = (bfd_byte *) (((ptrdiff_t) (data + align)) & ~ align);
5879bb8f 2580 rva_bias += data - p;
11a6da56
NC
2581
2582 /* For reasons that are unclear .rsrc sections are sometimes created
2583 aligned to a 1^3 boundary even when their alignment is set at
2584 1^2. Catch that case here before we issue a spurious warning
2585 message. */
3714081c
NC
2586 if (data == (regions.section_end - 4))
2587 data = regions.section_end;
2588 else if (data < regions.section_end)
c32abae8
NC
2589 {
2590 /* If the extra data is all zeros then do not complain.
2591 This is just padding so that the section meets the
2592 page size requirements. */
6937bb54 2593 while (++ data < regions.section_end)
c32abae8
NC
2594 if (*data != 0)
2595 break;
2596 if (data < regions.section_end)
2597 fprintf (file, _("\nWARNING: Extra data in .rsrc section - it will be ignored by Windows:\n"));
2598 }
11a6da56
NC
2599 }
2600 }
2601
3714081c 2602 if (regions.strings_start != NULL)
695344c0 2603 fprintf (file, _(" String table starts at offset: %#03x\n"),
08937d80 2604 (int) (regions.strings_start - regions.section_start));
3714081c 2605 if (regions.resource_start != NULL)
695344c0 2606 fprintf (file, _(" Resources start at offset: %#03x\n"),
08937d80 2607 (int) (regions.resource_start - regions.section_start));
1b786873 2608
3714081c 2609 free (regions.section_start);
11a6da56
NC
2610 return TRUE;
2611}
2612
61e2488c
JT
2613#define IMAGE_NUMBEROF_DEBUG_TYPES 12
2614
2615static char * debug_type_names[IMAGE_NUMBEROF_DEBUG_TYPES] =
2616{
2617 "Unknown",
2618 "COFF",
2619 "CodeView",
2620 "FPO",
2621 "Misc",
2622 "Exception",
2623 "Fixup",
2624 "OMAP-to-SRC",
2625 "OMAP-from-SRC",
2626 "Borland",
2627 "Reserved",
2628 "CLSID",
2629};
2630
2631static bfd_boolean
2632pe_print_debugdata (bfd * abfd, void * vfile)
2633{
2634 FILE *file = (FILE *) vfile;
2635 pe_data_type *pe = pe_data (abfd);
2636 struct internal_extra_pe_aouthdr *extra = &pe->pe_opthdr;
2637 asection *section;
2638 bfd_byte *data = 0;
2639 bfd_size_type dataoff;
2640 unsigned int i;
2641
2642 bfd_vma addr = extra->DataDirectory[PE_DEBUG_DATA].VirtualAddress;
2643 bfd_size_type size = extra->DataDirectory[PE_DEBUG_DATA].Size;
2644
2645 if (size == 0)
2646 return TRUE;
2647
2648 addr += extra->ImageBase;
2649 for (section = abfd->sections; section != NULL; section = section->next)
2650 {
2651 if ((addr >= section->vma) && (addr < (section->vma + section->size)))
07d6d2b8 2652 break;
61e2488c
JT
2653 }
2654
2655 if (section == NULL)
2656 {
2657 fprintf (file,
07d6d2b8 2658 _("\nThere is a debug directory, but the section containing it could not be found\n"));
61e2488c
JT
2659 return TRUE;
2660 }
6e6e7cfc
JT
2661 else if (!(section->flags & SEC_HAS_CONTENTS))
2662 {
2663 fprintf (file,
07d6d2b8
AM
2664 _("\nThere is a debug directory in %s, but that section has no contents\n"),
2665 section->name);
6e6e7cfc
JT
2666 return TRUE;
2667 }
5a3f568b
NC
2668 else if (section->size < size)
2669 {
2670 fprintf (file,
07d6d2b8
AM
2671 _("\nError: section %s contains the debug data starting address but it is too small\n"),
2672 section->name);
5a3f568b
NC
2673 return FALSE;
2674 }
61e2488c
JT
2675
2676 fprintf (file, _("\nThere is a debug directory in %s at 0x%lx\n\n"),
2677 section->name, (unsigned long) addr);
2678
2679 dataoff = addr - section->vma;
2680
a6f921c8
NC
2681 if (size > (section->size - dataoff))
2682 {
2683 fprintf (file, _("The debug data size field in the data directory is too big for the section"));
2684 return FALSE;
2685 }
2686
61e2488c
JT
2687 fprintf (file,
2688 _("Type Size Rva Offset\n"));
2689
5a3f568b 2690 /* Read the whole section. */
61e2488c
JT
2691 if (!bfd_malloc_and_get_section (abfd, section, &data))
2692 {
2693 if (data != NULL)
2694 free (data);
2695 return FALSE;
2696 }
2697
2698 for (i = 0; i < size / sizeof (struct external_IMAGE_DEBUG_DIRECTORY); i++)
2699 {
2700 const char *type_name;
2701 struct external_IMAGE_DEBUG_DIRECTORY *ext
2702 = &((struct external_IMAGE_DEBUG_DIRECTORY *)(data + dataoff))[i];
2703 struct internal_IMAGE_DEBUG_DIRECTORY idd;
2704
2705 _bfd_XXi_swap_debugdir_in (abfd, ext, &idd);
2706
20ad5e28 2707 if ((idd.Type) >= IMAGE_NUMBEROF_DEBUG_TYPES)
07d6d2b8 2708 type_name = debug_type_names[0];
61e2488c 2709 else
07d6d2b8 2710 type_name = debug_type_names[idd.Type];
61e2488c
JT
2711
2712 fprintf (file, " %2ld %14s %08lx %08lx %08lx\n",
2713 idd.Type, type_name, idd.SizeOfData,
2714 idd.AddressOfRawData, idd.PointerToRawData);
2715
2716 if (idd.Type == PE_IMAGE_DEBUG_TYPE_CODEVIEW)
07d6d2b8
AM
2717 {
2718 char signature[CV_INFO_SIGNATURE_LENGTH * 2 + 1];
77ef8654
NC
2719 /* PR 17512: file: 065-29434-0.001:0.1
2720 We need to use a 32-bit aligned buffer
2721 to safely read in a codeview record. */
07d6d2b8 2722 char buffer[256 + 1] ATTRIBUTE_ALIGNED_ALIGNOF (CODEVIEW_INFO);
77ef8654 2723
07d6d2b8 2724 CODEVIEW_INFO *cvinfo = (CODEVIEW_INFO *) buffer;
61e2488c 2725
07d6d2b8 2726 /* The debug entry doesn't have to have to be in a section,
61e2488c 2727 in which case AddressOfRawData is 0, so always use PointerToRawData. */
07d6d2b8 2728 if (!_bfd_XXi_slurp_codeview_record (abfd, (file_ptr) idd.PointerToRawData,
61e2488c 2729 idd.SizeOfData, cvinfo))
07d6d2b8 2730 continue;
61e2488c 2731
07d6d2b8
AM
2732 for (i = 0; i < cvinfo->SignatureLength; i++)
2733 sprintf (&signature[i*2], "%02x", cvinfo->Signature[i] & 0xff);
61e2488c 2734
695344c0 2735 /* xgettext:c-format */
07d6d2b8 2736 fprintf (file, _("(format %c%c%c%c signature %s age %ld)\n"),
61e2488c
JT
2737 buffer[0], buffer[1], buffer[2], buffer[3],
2738 signature, cvinfo->Age);
07d6d2b8 2739 }
61e2488c
JT
2740 }
2741
2742 if (size % sizeof (struct external_IMAGE_DEBUG_DIRECTORY) != 0)
2743 fprintf (file,
07d6d2b8 2744 _("The debug directory size is not a multiple of the debug directory entry size\n"));
61e2488c
JT
2745
2746 return TRUE;
2747}
2748
277d1b5e
ILT
2749/* Print out the program headers. */
2750
b34976b6 2751bfd_boolean
7920ce38 2752_bfd_XX_print_private_bfd_data_common (bfd * abfd, void * vfile)
277d1b5e
ILT
2753{
2754 FILE *file = (FILE *) vfile;
2755 int j;
2756 pe_data_type *pe = pe_data (abfd);
2757 struct internal_extra_pe_aouthdr *i = &pe->pe_opthdr;
fac41780 2758 const char *subsystem_name = NULL;
d13c9dc6 2759 const char *name;
277d1b5e
ILT
2760
2761 /* The MS dumpbin program reportedly ands with 0xff0f before
2762 printing the characteristics field. Not sure why. No reason to
2763 emulate it here. */
2764 fprintf (file, _("\nCharacteristics 0x%x\n"), pe->real_flags);
2765#undef PF
6fa957a9 2766#define PF(x, y) if (pe->real_flags & x) { fprintf (file, "\t%s\n", y); }
d70270c5
BF
2767 PF (IMAGE_FILE_RELOCS_STRIPPED, "relocations stripped");
2768 PF (IMAGE_FILE_EXECUTABLE_IMAGE, "executable");
2769 PF (IMAGE_FILE_LINE_NUMS_STRIPPED, "line numbers stripped");
2770 PF (IMAGE_FILE_LOCAL_SYMS_STRIPPED, "symbols stripped");
2771 PF (IMAGE_FILE_LARGE_ADDRESS_AWARE, "large address aware");
2772 PF (IMAGE_FILE_BYTES_REVERSED_LO, "little endian");
2773 PF (IMAGE_FILE_32BIT_MACHINE, "32 bit words");
2774 PF (IMAGE_FILE_DEBUG_STRIPPED, "debugging information removed");
2775 PF (IMAGE_FILE_SYSTEM, "system file");
2776 PF (IMAGE_FILE_DLL, "DLL");
2777 PF (IMAGE_FILE_BYTES_REVERSED_HI, "big endian");
277d1b5e
ILT
2778#undef PF
2779
5933bdc9 2780 /* ctime implies '\n'. */
0b6488e2
RH
2781 {
2782 time_t t = pe->coff.timestamp;
2783 fprintf (file, "\nTime/Date\t\t%s", ctime (&t));
2784 }
d13c9dc6
L
2785
2786#ifndef IMAGE_NT_OPTIONAL_HDR_MAGIC
2787# define IMAGE_NT_OPTIONAL_HDR_MAGIC 0x10b
2788#endif
2789#ifndef IMAGE_NT_OPTIONAL_HDR64_MAGIC
2790# define IMAGE_NT_OPTIONAL_HDR64_MAGIC 0x20b
2791#endif
2792#ifndef IMAGE_NT_OPTIONAL_HDRROM_MAGIC
2793# define IMAGE_NT_OPTIONAL_HDRROM_MAGIC 0x107
2794#endif
2795
2796 switch (i->Magic)
2797 {
2798 case IMAGE_NT_OPTIONAL_HDR_MAGIC:
2799 name = "PE32";
2800 break;
2801 case IMAGE_NT_OPTIONAL_HDR64_MAGIC:
2802 name = "PE32+";
2803 break;
2804 case IMAGE_NT_OPTIONAL_HDRROM_MAGIC:
2805 name = "ROM";
2806 break;
2807 default:
2808 name = NULL;
2809 break;
2810 }
2811 fprintf (file, "Magic\t\t\t%04x", i->Magic);
2812 if (name)
2813 fprintf (file, "\t(%s)",name);
2814 fprintf (file, "\nMajorLinkerVersion\t%d\n", i->MajorLinkerVersion);
2815 fprintf (file, "MinorLinkerVersion\t%d\n", i->MinorLinkerVersion);
b24cc414
AM
2816 fprintf (file, "SizeOfCode\t\t");
2817 bfd_fprintf_vma (abfd, file, i->SizeOfCode);
2818 fprintf (file, "\nSizeOfInitializedData\t");
2819 bfd_fprintf_vma (abfd, file, i->SizeOfInitializedData);
2820 fprintf (file, "\nSizeOfUninitializedData\t");
2821 bfd_fprintf_vma (abfd, file, i->SizeOfUninitializedData);
2822 fprintf (file, "\nAddressOfEntryPoint\t");
ebf12fbe 2823 bfd_fprintf_vma (abfd, file, i->AddressOfEntryPoint);
d13c9dc6 2824 fprintf (file, "\nBaseOfCode\t\t");
ebf12fbe 2825 bfd_fprintf_vma (abfd, file, i->BaseOfCode);
d13c9dc6
L
2826#if !defined(COFF_WITH_pep) && !defined(COFF_WITH_pex64)
2827 /* PE32+ does not have BaseOfData member! */
2828 fprintf (file, "\nBaseOfData\t\t");
ebf12fbe 2829 bfd_fprintf_vma (abfd, file, i->BaseOfData);
d13c9dc6
L
2830#endif
2831
9602af51 2832 fprintf (file, "\nImageBase\t\t");
ebf12fbe 2833 bfd_fprintf_vma (abfd, file, i->ImageBase);
b24cc414
AM
2834 fprintf (file, "\nSectionAlignment\t%08x\n", i->SectionAlignment);
2835 fprintf (file, "FileAlignment\t\t%08x\n", i->FileAlignment);
2836 fprintf (file, "MajorOSystemVersion\t%d\n", i->MajorOperatingSystemVersion);
9602af51
KH
2837 fprintf (file, "MinorOSystemVersion\t%d\n", i->MinorOperatingSystemVersion);
2838 fprintf (file, "MajorImageVersion\t%d\n", i->MajorImageVersion);
2839 fprintf (file, "MinorImageVersion\t%d\n", i->MinorImageVersion);
2840 fprintf (file, "MajorSubsystemVersion\t%d\n", i->MajorSubsystemVersion);
2841 fprintf (file, "MinorSubsystemVersion\t%d\n", i->MinorSubsystemVersion);
b24cc414
AM
2842 fprintf (file, "Win32Version\t\t%08x\n", i->Reserved1);
2843 fprintf (file, "SizeOfImage\t\t%08x\n", i->SizeOfImage);
2844 fprintf (file, "SizeOfHeaders\t\t%08x\n", i->SizeOfHeaders);
2845 fprintf (file, "CheckSum\t\t%08x\n", i->CheckSum);
1725a96e 2846
fac41780
JW
2847 switch (i->Subsystem)
2848 {
2849 case IMAGE_SUBSYSTEM_UNKNOWN:
2850 subsystem_name = "unspecified";
2851 break;
2852 case IMAGE_SUBSYSTEM_NATIVE:
2853 subsystem_name = "NT native";
2854 break;
2855 case IMAGE_SUBSYSTEM_WINDOWS_GUI:
2856 subsystem_name = "Windows GUI";
2857 break;
2858 case IMAGE_SUBSYSTEM_WINDOWS_CUI:
2859 subsystem_name = "Windows CUI";
2860 break;
2861 case IMAGE_SUBSYSTEM_POSIX_CUI:
2862 subsystem_name = "POSIX CUI";
2863 break;
2864 case IMAGE_SUBSYSTEM_WINDOWS_CE_GUI:
2865 subsystem_name = "Wince CUI";
2866 break;
d9118602 2867 // These are from UEFI Platform Initialization Specification 1.1.
fac41780
JW
2868 case IMAGE_SUBSYSTEM_EFI_APPLICATION:
2869 subsystem_name = "EFI application";
2870 break;
2871 case IMAGE_SUBSYSTEM_EFI_BOOT_SERVICE_DRIVER:
2872 subsystem_name = "EFI boot service driver";
2873 break;
2874 case IMAGE_SUBSYSTEM_EFI_RUNTIME_DRIVER:
9602af51 2875 subsystem_name = "EFI runtime driver";
fac41780 2876 break;
d9118602
L
2877 case IMAGE_SUBSYSTEM_SAL_RUNTIME_DRIVER:
2878 subsystem_name = "SAL runtime driver";
6c73cbb1 2879 break;
d9118602 2880 // This is from revision 8.0 of the MS PE/COFF spec
6c73cbb1
NC
2881 case IMAGE_SUBSYSTEM_XBOX:
2882 subsystem_name = "XBOX";
2883 break;
2884 // Added default case for clarity - subsystem_name is NULL anyway.
2885 default:
2886 subsystem_name = NULL;
fac41780 2887 }
1725a96e 2888
9602af51 2889 fprintf (file, "Subsystem\t\t%08x", i->Subsystem);
fac41780
JW
2890 if (subsystem_name)
2891 fprintf (file, "\t(%s)", subsystem_name);
9602af51
KH
2892 fprintf (file, "\nDllCharacteristics\t%08x\n", i->DllCharacteristics);
2893 fprintf (file, "SizeOfStackReserve\t");
ebf12fbe 2894 bfd_fprintf_vma (abfd, file, i->SizeOfStackReserve);
9602af51 2895 fprintf (file, "\nSizeOfStackCommit\t");
ebf12fbe 2896 bfd_fprintf_vma (abfd, file, i->SizeOfStackCommit);
9602af51 2897 fprintf (file, "\nSizeOfHeapReserve\t");
ebf12fbe 2898 bfd_fprintf_vma (abfd, file, i->SizeOfHeapReserve);
9602af51 2899 fprintf (file, "\nSizeOfHeapCommit\t");
ebf12fbe 2900 bfd_fprintf_vma (abfd, file, i->SizeOfHeapCommit);
0af1713e
AM
2901 fprintf (file, "\nLoaderFlags\t\t%08lx\n", (unsigned long) i->LoaderFlags);
2902 fprintf (file, "NumberOfRvaAndSizes\t%08lx\n",
2903 (unsigned long) i->NumberOfRvaAndSizes);
277d1b5e 2904
9602af51 2905 fprintf (file, "\nThe Data Directory\n");
277d1b5e
ILT
2906 for (j = 0; j < IMAGE_NUMBEROF_DIRECTORY_ENTRIES; j++)
2907 {
2908 fprintf (file, "Entry %1x ", j);
ebf12fbe 2909 bfd_fprintf_vma (abfd, file, i->DataDirectory[j].VirtualAddress);
0af1713e 2910 fprintf (file, " %08lx ", (unsigned long) i->DataDirectory[j].Size);
277d1b5e
ILT
2911 fprintf (file, "%s\n", dir_names[j]);
2912 }
2913
2914 pe_print_idata (abfd, vfile);
2915 pe_print_edata (abfd, vfile);
2b5c217d
NC
2916 if (bfd_coff_have_print_pdata (abfd))
2917 bfd_coff_print_pdata (abfd, vfile);
2918 else
2919 pe_print_pdata (abfd, vfile);
277d1b5e 2920 pe_print_reloc (abfd, vfile);
61e2488c 2921 pe_print_debugdata (abfd, file);
277d1b5e 2922
5879bb8f 2923 rsrc_print_section (abfd, vfile);
9373215c 2924
b34976b6 2925 return TRUE;
277d1b5e
ILT
2926}
2927
6e6e7cfc
JT
2928static bfd_boolean
2929is_vma_in_section (bfd *abfd ATTRIBUTE_UNUSED, asection *sect, void *obj)
2930{
2931 bfd_vma addr = * (bfd_vma *) obj;
2932 return (addr >= sect->vma) && (addr < (sect->vma + sect->size));
2933}
2934
2935static asection *
2936find_section_by_vma (bfd *abfd, bfd_vma addr)
2937{
2938 return bfd_sections_find_if (abfd, is_vma_in_section, (void *) & addr);
2939}
2940
277d1b5e
ILT
2941/* Copy any private info we understand from the input bfd
2942 to the output bfd. */
2943
b34976b6 2944bfd_boolean
7920ce38 2945_bfd_XX_bfd_copy_private_bfd_data_common (bfd * ibfd, bfd * obfd)
277d1b5e 2946{
4be8cddc
L
2947 pe_data_type *ipe, *ope;
2948
277d1b5e
ILT
2949 /* One day we may try to grok other private data. */
2950 if (ibfd->xvec->flavour != bfd_target_coff_flavour
2951 || obfd->xvec->flavour != bfd_target_coff_flavour)
b34976b6 2952 return TRUE;
277d1b5e 2953
4be8cddc
L
2954 ipe = pe_data (ibfd);
2955 ope = pe_data (obfd);
4e1fc599 2956
325c681d 2957 /* pe_opthdr is copied in copy_object. */
4be8cddc
L
2958 ope->dll = ipe->dll;
2959
2960 /* Don't copy input subsystem if output is different from input. */
2961 if (obfd->xvec != ibfd->xvec)
2962 ope->pe_opthdr.Subsystem = IMAGE_SUBSYSTEM_UNKNOWN;
277d1b5e 2963
1725a96e 2964 /* For strip: if we removed .reloc, we'll make a real mess of things
5933bdc9
ILT
2965 if we don't remove this entry as well. */
2966 if (! pe_data (obfd)->has_reloc_section)
2967 {
6c73cbb1
NC
2968 pe_data (obfd)->pe_opthdr.DataDirectory[PE_BASE_RELOCATION_TABLE].VirtualAddress = 0;
2969 pe_data (obfd)->pe_opthdr.DataDirectory[PE_BASE_RELOCATION_TABLE].Size = 0;
5933bdc9 2970 }
441f34fa
L
2971
2972 /* For PIE, if there is .reloc, we won't add IMAGE_FILE_RELOCS_STRIPPED.
2973 But there is no .reloc, we make sure that IMAGE_FILE_RELOCS_STRIPPED
2974 won't be added. */
2975 if (! pe_data (ibfd)->has_reloc_section
2976 && ! (pe_data (ibfd)->real_flags & IMAGE_FILE_RELOCS_STRIPPED))
2977 pe_data (obfd)->dont_strip_reloc = 1;
2978
6e6e7cfc
JT
2979 /* The file offsets contained in the debug directory need rewriting. */
2980 if (ope->pe_opthdr.DataDirectory[PE_DEBUG_DATA].Size != 0)
2981 {
2982 bfd_vma addr = ope->pe_opthdr.DataDirectory[PE_DEBUG_DATA].VirtualAddress
2983 + ope->pe_opthdr.ImageBase;
2984 asection *section = find_section_by_vma (obfd, addr);
2985 bfd_byte *data;
2986
2987 if (section && bfd_malloc_and_get_section (obfd, section, &data))
07d6d2b8
AM
2988 {
2989 unsigned int i;
2990 struct external_IMAGE_DEBUG_DIRECTORY *dd =
6e6e7cfc
JT
2991 (struct external_IMAGE_DEBUG_DIRECTORY *)(data + (addr - section->vma));
2992
063bb025 2993 /* PR 17512: file: 0f15796a. */
48dcd4ea
AM
2994 if ((unsigned long) ope->pe_opthdr.DataDirectory[PE_DEBUG_DATA].Size
2995 > section->size - (addr - section->vma))
063bb025 2996 {
695344c0 2997 /* xgettext:c-format */
2dcf00ce
AM
2998 _bfd_error_handler
2999 (_("%pB: Data Directory size (%lx) "
3000 "exceeds space left in section (%" PRIx64 ")"),
3001 obfd, ope->pe_opthdr.DataDirectory[PE_DEBUG_DATA].Size,
3002 (uint64_t) (section->size - (addr - section->vma)));
8df73d5c 3003 free (data);
aa4a8c2a
NC
3004 return FALSE;
3005 }
063bb025 3006
07d6d2b8 3007 for (i = 0; i < ope->pe_opthdr.DataDirectory[PE_DEBUG_DATA].Size
6e6e7cfc 3008 / sizeof (struct external_IMAGE_DEBUG_DIRECTORY); i++)
07d6d2b8
AM
3009 {
3010 asection *ddsection;
3011 struct external_IMAGE_DEBUG_DIRECTORY *edd = &(dd[i]);
3012 struct internal_IMAGE_DEBUG_DIRECTORY idd;
6e6e7cfc 3013
07d6d2b8 3014 _bfd_XXi_swap_debugdir_in (obfd, edd, &idd);
6e6e7cfc 3015
07d6d2b8
AM
3016 if (idd.AddressOfRawData == 0)
3017 continue; /* RVA 0 means only offset is valid, not handled yet. */
6e6e7cfc 3018
07d6d2b8
AM
3019 ddsection = find_section_by_vma (obfd, idd.AddressOfRawData + ope->pe_opthdr.ImageBase);
3020 if (!ddsection)
3021 continue; /* Not in a section! */
6e6e7cfc 3022
07d6d2b8 3023 idd.PointerToRawData = ddsection->filepos + (idd.AddressOfRawData
6e6e7cfc
JT
3024 + ope->pe_opthdr.ImageBase) - ddsection->vma;
3025
07d6d2b8
AM
3026 _bfd_XXi_swap_debugdir_out (obfd, &idd, edd);
3027 }
6e6e7cfc 3028
07d6d2b8 3029 if (!bfd_set_section_contents (obfd, section, data, 0, section->size))
86eafac0 3030 {
59d08d6c 3031 _bfd_error_handler (_("failed to update file offsets in debug directory"));
8df73d5c 3032 free (data);
86eafac0
NC
3033 return FALSE;
3034 }
8df73d5c 3035 free (data);
07d6d2b8 3036 }
86eafac0
NC
3037 else if (section)
3038 {
59d08d6c 3039 _bfd_error_handler (_("%pB: failed to read debug data section"), obfd);
86eafac0
NC
3040 return FALSE;
3041 }
6e6e7cfc
JT
3042 }
3043
b34976b6 3044 return TRUE;
277d1b5e
ILT
3045}
3046
9602af51 3047/* Copy private section data. */
1725a96e 3048
b34976b6 3049bfd_boolean
7920ce38
NC
3050_bfd_XX_bfd_copy_private_section_data (bfd *ibfd,
3051 asection *isec,
3052 bfd *obfd,
3053 asection *osec)
277d1b5e
ILT
3054{
3055 if (bfd_get_flavour (ibfd) != bfd_target_coff_flavour
3056 || bfd_get_flavour (obfd) != bfd_target_coff_flavour)
b34976b6 3057 return TRUE;
277d1b5e
ILT
3058
3059 if (coff_section_data (ibfd, isec) != NULL
3060 && pei_section_data (ibfd, isec) != NULL)
3061 {
3062 if (coff_section_data (obfd, osec) == NULL)
3063 {
dc810e39 3064 bfd_size_type amt = sizeof (struct coff_section_tdata);
7920ce38 3065 osec->used_by_bfd = bfd_zalloc (obfd, amt);
277d1b5e 3066 if (osec->used_by_bfd == NULL)
b34976b6 3067 return FALSE;
277d1b5e 3068 }
1725a96e 3069
277d1b5e
ILT
3070 if (pei_section_data (obfd, osec) == NULL)
3071 {
dc810e39 3072 bfd_size_type amt = sizeof (struct pei_section_tdata);
7920ce38 3073 coff_section_data (obfd, osec)->tdata = bfd_zalloc (obfd, amt);
277d1b5e 3074 if (coff_section_data (obfd, osec)->tdata == NULL)
b34976b6 3075 return FALSE;
277d1b5e 3076 }
1725a96e 3077
277d1b5e
ILT
3078 pei_section_data (obfd, osec)->virt_size =
3079 pei_section_data (ibfd, isec)->virt_size;
5933bdc9 3080 pei_section_data (obfd, osec)->pe_flags =
6fa957a9 3081 pei_section_data (ibfd, isec)->pe_flags;
277d1b5e
ILT
3082 }
3083
b34976b6 3084 return TRUE;
277d1b5e 3085}
7d2b58d6
ILT
3086
3087void
7920ce38 3088_bfd_XX_get_symbol_info (bfd * abfd, asymbol *symbol, symbol_info *ret)
7d2b58d6
ILT
3089{
3090 coff_get_symbol_info (abfd, symbol, ret);
7d2b58d6 3091}
2fbadf2c 3092
5174d0fb
KT
3093#if !defined(COFF_WITH_pep) && defined(COFF_WITH_pex64)
3094static int
3095sort_x64_pdata (const void *l, const void *r)
3096{
3097 const char *lp = (const char *) l;
3098 const char *rp = (const char *) r;
3099 bfd_vma vl, vr;
3100 vl = bfd_getl32 (lp); vr = bfd_getl32 (rp);
3101 if (vl != vr)
3102 return (vl < vr ? -1 : 1);
3103 /* We compare just begin address. */
3104 return 0;
3105}
3106#endif
5879bb8f
NC
3107\f
3108/* Functions to process a .rsrc section. */
3109
3110static unsigned int sizeof_leaves;
3111static unsigned int sizeof_strings;
3112static unsigned int sizeof_tables_and_entries;
3113
3114static bfd_byte *
3115rsrc_count_directory (bfd *, bfd_byte *, bfd_byte *, bfd_byte *, bfd_vma);
3116
3117static bfd_byte *
07d6d2b8
AM
3118rsrc_count_entries (bfd * abfd,
3119 bfd_boolean is_name,
3120 bfd_byte * datastart,
3121 bfd_byte * data,
3122 bfd_byte * dataend,
3123 bfd_vma rva_bias)
5879bb8f
NC
3124{
3125 unsigned long entry, addr, size;
3126
3127 if (data + 8 >= dataend)
3128 return dataend + 1;
3129
3130 if (is_name)
3131 {
3132 bfd_byte * name;
3133
3134 entry = (long) bfd_get_32 (abfd, data);
3135
3136 if (HighBitSet (entry))
3137 name = datastart + WithoutHighBit (entry);
3138 else
3139 name = datastart + entry - rva_bias;
3140
20ad5e28 3141 if (name + 2 >= dataend || name < datastart)
5879bb8f
NC
3142 return dataend + 1;
3143
3144 unsigned int len = bfd_get_16 (abfd, name);
3145 if (len == 0 || len > 256)
3146 return dataend + 1;
5879bb8f
NC
3147 }
3148
3149 entry = (long) bfd_get_32 (abfd, data + 4);
3150
3151 if (HighBitSet (entry))
20ad5e28
NC
3152 {
3153 data = datastart + WithoutHighBit (entry);
3154
3155 if (data <= datastart || data >= dataend)
3156 return dataend + 1;
3157
3158 return rsrc_count_directory (abfd, datastart, data, dataend, rva_bias);
3159 }
5879bb8f
NC
3160
3161 if (datastart + entry + 16 >= dataend)
3162 return dataend + 1;
3163
3164 addr = (long) bfd_get_32 (abfd, datastart + entry);
3165 size = (long) bfd_get_32 (abfd, datastart + entry + 4);
3166
5879bb8f
NC
3167 return datastart + addr - rva_bias + size;
3168}
9373215c 3169
5879bb8f 3170static bfd_byte *
07d6d2b8 3171rsrc_count_directory (bfd * abfd,
5879bb8f
NC
3172 bfd_byte * datastart,
3173 bfd_byte * data,
3174 bfd_byte * dataend,
07d6d2b8 3175 bfd_vma rva_bias)
5879bb8f
NC
3176{
3177 unsigned int num_entries, num_ids;
3178 bfd_byte * highest_data = data;
3179
3180 if (data + 16 >= dataend)
3181 return dataend + 1;
3182
3183 num_entries = (int) bfd_get_16 (abfd, data + 12);
3184 num_ids = (int) bfd_get_16 (abfd, data + 14);
3185
3186 num_entries += num_ids;
3187
3188 data += 16;
5879bb8f
NC
3189
3190 while (num_entries --)
3191 {
3192 bfd_byte * entry_end;
3193
3194 entry_end = rsrc_count_entries (abfd, num_entries >= num_ids,
3195 datastart, data, dataend, rva_bias);
3196 data += 8;
5879bb8f
NC
3197 highest_data = max (highest_data, entry_end);
3198 if (entry_end >= dataend)
3199 break;
3200 }
3201
3202 return max (highest_data, data);
3203}
3204
3205typedef struct rsrc_dir_chain
3206{
07d6d2b8 3207 unsigned int num_entries;
5879bb8f
NC
3208 struct rsrc_entry * first_entry;
3209 struct rsrc_entry * last_entry;
3210} rsrc_dir_chain;
3211
3212typedef struct rsrc_directory
3213{
3214 unsigned int characteristics;
3215 unsigned int time;
3216 unsigned int major;
3217 unsigned int minor;
3218
3219 rsrc_dir_chain names;
3220 rsrc_dir_chain ids;
3221
3222 struct rsrc_entry * entry;
3223} rsrc_directory;
3224
3225typedef struct rsrc_string
3226{
07d6d2b8
AM
3227 unsigned int len;
3228 bfd_byte * string;
5879bb8f 3229} rsrc_string;
9373215c 3230
5879bb8f
NC
3231typedef struct rsrc_leaf
3232{
07d6d2b8
AM
3233 unsigned int size;
3234 unsigned int codepage;
3235 bfd_byte * data;
5879bb8f
NC
3236} rsrc_leaf;
3237
3238typedef struct rsrc_entry
3239{
3240 bfd_boolean is_name;
3241 union
3242 {
07d6d2b8
AM
3243 unsigned int id;
3244 struct rsrc_string name;
5879bb8f
NC
3245 } name_id;
3246
3247 bfd_boolean is_dir;
3248 union
3249 {
3250 struct rsrc_directory * directory;
07d6d2b8 3251 struct rsrc_leaf * leaf;
5879bb8f
NC
3252 } value;
3253
07d6d2b8 3254 struct rsrc_entry * next_entry;
5879bb8f
NC
3255 struct rsrc_directory * parent;
3256} rsrc_entry;
3257
3258static bfd_byte *
3259rsrc_parse_directory (bfd *, rsrc_directory *, bfd_byte *,
3260 bfd_byte *, bfd_byte *, bfd_vma, rsrc_entry *);
3261
3262static bfd_byte *
07d6d2b8
AM
3263rsrc_parse_entry (bfd * abfd,
3264 bfd_boolean is_name,
3265 rsrc_entry * entry,
3266 bfd_byte * datastart,
3267 bfd_byte * data,
3268 bfd_byte * dataend,
3269 bfd_vma rva_bias,
5879bb8f
NC
3270 rsrc_directory * parent)
3271{
3272 unsigned long val, addr, size;
3273
3274 val = bfd_get_32 (abfd, data);
3275
3276 entry->parent = parent;
3277 entry->is_name = is_name;
3278
3279 if (is_name)
3280 {
20ad5e28
NC
3281 bfd_byte * address;
3282
5879bb8f
NC
3283 if (HighBitSet (val))
3284 {
3285 val = WithoutHighBit (val);
3286
20ad5e28 3287 address = datastart + val;
5879bb8f
NC
3288 }
3289 else
3290 {
20ad5e28 3291 address = datastart + val - rva_bias;
5879bb8f 3292 }
20ad5e28
NC
3293
3294 if (address + 3 > dataend)
3295 return dataend;
3296
3297 entry->name_id.name.len = bfd_get_16 (abfd, address);
3298 entry->name_id.name.string = address + 2;
5879bb8f
NC
3299 }
3300 else
3301 entry->name_id.id = val;
3302
3303 val = bfd_get_32 (abfd, data + 4);
3304
3305 if (HighBitSet (val))
3306 {
3307 entry->is_dir = TRUE;
3308 entry->value.directory = bfd_malloc (sizeof * entry->value.directory);
3309 if (entry->value.directory == NULL)
3310 return dataend;
3311
3312 return rsrc_parse_directory (abfd, entry->value.directory,
3313 datastart,
3314 datastart + WithoutHighBit (val),
3315 dataend, rva_bias, entry);
3316 }
3317
3318 entry->is_dir = FALSE;
3319 entry->value.leaf = bfd_malloc (sizeof * entry->value.leaf);
3320 if (entry->value.leaf == NULL)
3321 return dataend;
3322
5929c344
NC
3323 data = datastart + val;
3324 if (data < datastart || data >= dataend)
3325 return dataend;
3326
3327 addr = bfd_get_32 (abfd, data);
3328 size = entry->value.leaf->size = bfd_get_32 (abfd, data + 4);
3329 entry->value.leaf->codepage = bfd_get_32 (abfd, data + 8);
3330 /* FIXME: We assume that the reserved field (data + 12) is OK. */
5879bb8f
NC
3331
3332 entry->value.leaf->data = bfd_malloc (size);
3333 if (entry->value.leaf->data == NULL)
3334 return dataend;
3335
3336 memcpy (entry->value.leaf->data, datastart + addr - rva_bias, size);
3337 return datastart + (addr - rva_bias) + size;
3338}
3339
3340static bfd_byte *
07d6d2b8 3341rsrc_parse_entries (bfd * abfd,
5879bb8f 3342 rsrc_dir_chain * chain,
07d6d2b8
AM
3343 bfd_boolean is_name,
3344 bfd_byte * highest_data,
3345 bfd_byte * datastart,
3346 bfd_byte * data,
3347 bfd_byte * dataend,
3348 bfd_vma rva_bias,
5879bb8f
NC
3349 rsrc_directory * parent)
3350{
9373215c 3351 unsigned int i;
5879bb8f
NC
3352 rsrc_entry * entry;
3353
3354 if (chain->num_entries == 0)
3355 {
3356 chain->first_entry = chain->last_entry = NULL;
3357 return highest_data;
3358 }
3359
3360 entry = bfd_malloc (sizeof * entry);
3361 if (entry == NULL)
3362 return dataend;
3363
3364 chain->first_entry = entry;
3365
5879bb8f
NC
3366 for (i = chain->num_entries; i--;)
3367 {
3368 bfd_byte * entry_end;
3369
3370 entry_end = rsrc_parse_entry (abfd, is_name, entry, datastart,
3371 data, dataend, rva_bias, parent);
3372 data += 8;
3373 highest_data = max (entry_end, highest_data);
3374 if (entry_end > dataend)
3375 return dataend;
3376
3377 if (i)
3378 {
3379 entry->next_entry = bfd_malloc (sizeof * entry);
3380 entry = entry->next_entry;
3381 if (entry == NULL)
3382 return dataend;
3383 }
3384 else
3385 entry->next_entry = NULL;
3386 }
3387
3388 chain->last_entry = entry;
3389
3390 return highest_data;
3391}
3392
3393static bfd_byte *
07d6d2b8 3394rsrc_parse_directory (bfd * abfd,
5879bb8f
NC
3395 rsrc_directory * table,
3396 bfd_byte * datastart,
3397 bfd_byte * data,
3398 bfd_byte * dataend,
07d6d2b8 3399 bfd_vma rva_bias,
5879bb8f
NC
3400 rsrc_entry * entry)
3401{
3402 bfd_byte * highest_data = data;
3403
3404 if (table == NULL)
3405 return dataend;
3406
3407 table->characteristics = bfd_get_32 (abfd, data);
3408 table->time = bfd_get_32 (abfd, data + 4);
3409 table->major = bfd_get_16 (abfd, data + 8);
3410 table->minor = bfd_get_16 (abfd, data + 10);
3411 table->names.num_entries = bfd_get_16 (abfd, data + 12);
3412 table->ids.num_entries = bfd_get_16 (abfd, data + 14);
3413 table->entry = entry;
3414
3415 data += 16;
3416
3417 highest_data = rsrc_parse_entries (abfd, & table->names, TRUE, data,
3418 datastart, data, dataend, rva_bias, table);
3419 data += table->names.num_entries * 8;
3420
3421 highest_data = rsrc_parse_entries (abfd, & table->ids, FALSE, highest_data,
3422 datastart, data, dataend, rva_bias, table);
3423 data += table->ids.num_entries * 8;
3424
3425 return max (highest_data, data);
3426}
3427
3428typedef struct rsrc_write_data
3429{
3430 bfd * abfd;
3431 bfd_byte * datastart;
3432 bfd_byte * next_table;
3433 bfd_byte * next_leaf;
3434 bfd_byte * next_string;
3435 bfd_byte * next_data;
3436 bfd_vma rva_bias;
9373215c
PM
3437} rsrc_write_data;
3438
5879bb8f
NC
3439static void
3440rsrc_write_string (rsrc_write_data * data,
3441 rsrc_string * string)
3442{
3443 bfd_put_16 (data->abfd, string->len, data->next_string);
3444 memcpy (data->next_string + 2, string->string, string->len * 2);
3445 data->next_string += (string->len + 1) * 2;
3446}
3447
3448static inline unsigned int
3449rsrc_compute_rva (rsrc_write_data * data,
07d6d2b8 3450 bfd_byte * addr)
5879bb8f
NC
3451{
3452 return (addr - data->datastart) + data->rva_bias;
3453}
3454
3455static void
3456rsrc_write_leaf (rsrc_write_data * data,
07d6d2b8 3457 rsrc_leaf * leaf)
5879bb8f 3458{
9373215c
PM
3459 bfd_put_32 (data->abfd, rsrc_compute_rva (data, data->next_data),
3460 data->next_leaf);
5879bb8f
NC
3461 bfd_put_32 (data->abfd, leaf->size, data->next_leaf + 4);
3462 bfd_put_32 (data->abfd, leaf->codepage, data->next_leaf + 8);
3463 bfd_put_32 (data->abfd, 0 /*reserved*/, data->next_leaf + 12);
3464 data->next_leaf += 16;
3465
3466 memcpy (data->next_data, leaf->data, leaf->size);
3714081c
NC
3467 /* An undocumented feature of Windows resources is that each unit
3468 of raw data is 8-byte aligned... */
3469 data->next_data += ((leaf->size + 7) & ~7);
5879bb8f
NC
3470}
3471
3472static void rsrc_write_directory (rsrc_write_data *, rsrc_directory *);
3473
3474static void
3475rsrc_write_entry (rsrc_write_data * data,
07d6d2b8
AM
3476 bfd_byte * where,
3477 rsrc_entry * entry)
5879bb8f
NC
3478{
3479 if (entry->is_name)
3480 {
3481 bfd_put_32 (data->abfd,
3482 SetHighBit (data->next_string - data->datastart),
3483 where);
3484 rsrc_write_string (data, & entry->name_id.name);
3485 }
3486 else
3487 bfd_put_32 (data->abfd, entry->name_id.id, where);
3488
3489 if (entry->is_dir)
3490 {
3491 bfd_put_32 (data->abfd,
3492 SetHighBit (data->next_table - data->datastart),
3493 where + 4);
3494 rsrc_write_directory (data, entry->value.directory);
3495 }
3496 else
3497 {
3498 bfd_put_32 (data->abfd, data->next_leaf - data->datastart, where + 4);
3499 rsrc_write_leaf (data, entry->value.leaf);
3500 }
3501}
3502
3714081c
NC
3503static void
3504rsrc_compute_region_sizes (rsrc_directory * dir)
3505{
3506 struct rsrc_entry * entry;
3507
3508 if (dir == NULL)
3509 return;
3510
3511 sizeof_tables_and_entries += 16;
3512
3513 for (entry = dir->names.first_entry; entry != NULL; entry = entry->next_entry)
3514 {
3515 sizeof_tables_and_entries += 8;
3516
3517 sizeof_strings += (entry->name_id.name.len + 1) * 2;
1b786873 3518
3714081c
NC
3519 if (entry->is_dir)
3520 rsrc_compute_region_sizes (entry->value.directory);
3521 else
3522 sizeof_leaves += 16;
3523 }
3524
3525 for (entry = dir->ids.first_entry; entry != NULL; entry = entry->next_entry)
3526 {
3527 sizeof_tables_and_entries += 8;
3528
3529 if (entry->is_dir)
3530 rsrc_compute_region_sizes (entry->value.directory);
3531 else
3532 sizeof_leaves += 16;
3533 }
3534}
3535
5879bb8f
NC
3536static void
3537rsrc_write_directory (rsrc_write_data * data,
3538 rsrc_directory * dir)
3539{
3540 rsrc_entry * entry;
3541 unsigned int i;
9373215c
PM
3542 bfd_byte * next_entry;
3543 bfd_byte * nt;
5879bb8f
NC
3544
3545 bfd_put_32 (data->abfd, dir->characteristics, data->next_table);
3546 bfd_put_32 (data->abfd, 0 /*dir->time*/, data->next_table + 4);
3547 bfd_put_16 (data->abfd, dir->major, data->next_table + 8);
3548 bfd_put_16 (data->abfd, dir->minor, data->next_table + 10);
3549 bfd_put_16 (data->abfd, dir->names.num_entries, data->next_table + 12);
3550 bfd_put_16 (data->abfd, dir->ids.num_entries, data->next_table + 14);
3551
3552 /* Compute where the entries and the next table will be placed. */
9373215c
PM
3553 next_entry = data->next_table + 16;
3554 data->next_table = next_entry + (dir->names.num_entries * 8)
3555 + (dir->ids.num_entries * 8);
3556 nt = data->next_table;
3557
5879bb8f
NC
3558 /* Write the entries. */
3559 for (i = dir->names.num_entries, entry = dir->names.first_entry;
3560 i > 0 && entry != NULL;
3561 i--, entry = entry->next_entry)
3562 {
3714081c 3563 BFD_ASSERT (entry->is_name);
5879bb8f
NC
3564 rsrc_write_entry (data, next_entry, entry);
3565 next_entry += 8;
3566 }
3567 BFD_ASSERT (i == 0);
3568 BFD_ASSERT (entry == NULL);
3569
3570 for (i = dir->ids.num_entries, entry = dir->ids.first_entry;
3571 i > 0 && entry != NULL;
3572 i--, entry = entry->next_entry)
3573 {
3714081c 3574 BFD_ASSERT (! entry->is_name);
5879bb8f
NC
3575 rsrc_write_entry (data, next_entry, entry);
3576 next_entry += 8;
3577 }
3578 BFD_ASSERT (i == 0);
3579 BFD_ASSERT (entry == NULL);
3580 BFD_ASSERT (nt == next_entry);
3581}
3582
9373215c 3583#if defined HAVE_WCHAR_H && ! defined __CYGWIN__ && ! defined __MINGW32__
5879bb8f
NC
3584/* Return the length (number of units) of the first character in S,
3585 putting its 'ucs4_t' representation in *PUC. */
3586
3587static unsigned int
31593e1b
NC
3588#if defined HAVE_WCTYPE_H
3589u16_mbtouc (wint_t * puc, const unsigned short * s, unsigned int n)
3590#else
5879bb8f 3591u16_mbtouc (wchar_t * puc, const unsigned short * s, unsigned int n)
31593e1b 3592#endif
5879bb8f
NC
3593{
3594 unsigned short c = * s;
3595
3596 if (c < 0xd800 || c >= 0xe000)
3597 {
3598 *puc = c;
3599 return 1;
3600 }
3601
3602 if (c < 0xdc00)
3603 {
3604 if (n >= 2)
07d6d2b8
AM
3605 {
3606 if (s[1] >= 0xdc00 && s[1] < 0xe000)
3607 {
3608 *puc = 0x10000 + ((c - 0xd800) << 10) + (s[1] - 0xdc00);
3609 return 2;
3610 }
3611 }
5879bb8f 3612 else
07d6d2b8
AM
3613 {
3614 /* Incomplete multibyte character. */
3615 *puc = 0xfffd;
3616 return n;
3617 }
5879bb8f
NC
3618 }
3619
3620 /* Invalid multibyte character. */
3621 *puc = 0xfffd;
3622 return 1;
3623}
9373215c 3624#endif /* HAVE_WCHAR_H and not Cygwin/Mingw */
5879bb8f
NC
3625
3626/* Perform a comparison of two entries. */
3627static signed int
3628rsrc_cmp (bfd_boolean is_name, rsrc_entry * a, rsrc_entry * b)
3629{
9373215c 3630 signed int res;
9373215c
PM
3631 bfd_byte * astring;
3632 unsigned int alen;
3633 bfd_byte * bstring;
3634 unsigned int blen;
3635
5879bb8f 3636 if (! is_name)
9373215c 3637 return a->name_id.id - b->name_id.id;
5879bb8f
NC
3638
3639 /* We have to perform a case insenstive, unicode string comparison... */
9373215c
PM
3640 astring = a->name_id.name.string;
3641 alen = a->name_id.name.len;
3642 bstring = b->name_id.name.string;
3643 blen = b->name_id.name.len;
5879bb8f 3644
9373215c
PM
3645#if defined __CYGWIN__ || defined __MINGW32__
3646 /* Under Windows hosts (both Cygwin and Mingw types),
3647 unicode == UTF-16 == wchar_t. The case insensitive string comparison
3648 function however goes by different names in the two environments... */
3649
3650#undef rscpcmp
5879bb8f 3651#ifdef __CYGWIN__
9373215c
PM
3652#define rscpcmp wcsncasecmp
3653#endif
3654#ifdef __MINGW32__
3655#define rscpcmp wcsnicmp
3656#endif
3657
3658 res = rscpcmp ((const wchar_t *) astring, (const wchar_t *) bstring,
3659 min (alen, blen));
5879bb8f 3660
9373215c 3661#elif defined HAVE_WCHAR_H
3f10b67a
PM
3662 {
3663 unsigned int i;
31593e1b 3664
3f10b67a
PM
3665 res = 0;
3666 for (i = min (alen, blen); i--; astring += 2, bstring += 2)
3667 {
31593e1b
NC
3668#if defined HAVE_WCTYPE_H
3669 wint_t awc;
3670 wint_t bwc;
3671#else
3f10b67a
PM
3672 wchar_t awc;
3673 wchar_t bwc;
31593e1b 3674#endif
3f10b67a 3675
31593e1b
NC
3676 /* Convert UTF-16 unicode characters into wchar_t characters
3677 so that we can then perform a case insensitive comparison. */
3678 unsigned int Alen = u16_mbtouc (& awc, (const unsigned short *) astring, 2);
3679 unsigned int Blen = u16_mbtouc (& bwc, (const unsigned short *) bstring, 2);
3f10b67a
PM
3680
3681 if (Alen != Blen)
3682 return Alen - Blen;
31593e1b
NC
3683
3684#ifdef HAVE_WCTYPE_H
3685 awc = towlower (awc);
3686 bwc = towlower (bwc);
3687
3688 res = awc - bwc;
3689#else
3f10b67a 3690 res = wcsncasecmp (& awc, & bwc, 1);
31593e1b 3691#endif
3f10b67a
PM
3692 if (res)
3693 break;
3694 }
3695 }
5879bb8f 3696#else
9373215c
PM
3697 /* Do the best we can - a case sensitive, untranslated comparison. */
3698 res = memcmp (astring, bstring, min (alen, blen) * 2);
5879bb8f
NC
3699#endif
3700
3701 if (res == 0)
3702 res = alen - blen;
3703
3704 return res;
3705}
3706
3707static void
3708rsrc_print_name (char * buffer, rsrc_string string)
3709{
3710 unsigned int i;
3711 bfd_byte * name = string.string;
3712
3713 for (i = string.len; i--; name += 2)
3714 sprintf (buffer + strlen (buffer), "%.1s", name);
3715}
3716
3717static const char *
3718rsrc_resource_name (rsrc_entry * entry, rsrc_directory * dir)
3719{
3720 static char buffer [256];
3721 bfd_boolean is_string = FALSE;
3722
3723 buffer[0] = 0;
3724
9373215c
PM
3725 if (dir != NULL && dir->entry != NULL && dir->entry->parent != NULL
3726 && dir->entry->parent->entry != NULL)
5879bb8f
NC
3727 {
3728 strcpy (buffer, "type: ");
3729 if (dir->entry->parent->entry->is_name)
9373215c
PM
3730 rsrc_print_name (buffer + strlen (buffer),
3731 dir->entry->parent->entry->name_id.name);
5879bb8f
NC
3732 else
3733 {
3734 unsigned int id = dir->entry->parent->entry->name_id.id;
3735
3736 sprintf (buffer + strlen (buffer), "%x", id);
3737 switch (id)
3738 {
3739 case 1: strcat (buffer, " (CURSOR)"); break;
3740 case 2: strcat (buffer, " (BITMAP)"); break;
3741 case 3: strcat (buffer, " (ICON)"); break;
07d6d2b8 3742 case 4: strcat (buffer, " (MENU)"); break;
5879bb8f
NC
3743 case 5: strcat (buffer, " (DIALOG)"); break;
3744 case 6: strcat (buffer, " (STRING)"); is_string = TRUE; break;
3745 case 7: strcat (buffer, " (FONTDIR)"); break;
3746 case 8: strcat (buffer, " (FONT)"); break;
3747 case 9: strcat (buffer, " (ACCELERATOR)"); break;
3748 case 10: strcat (buffer, " (RCDATA)"); break;
3749 case 11: strcat (buffer, " (MESSAGETABLE)"); break;
3750 case 12: strcat (buffer, " (GROUP_CURSOR)"); break;
3751 case 14: strcat (buffer, " (GROUP_ICON)"); break;
3752 case 16: strcat (buffer, " (VERSION)"); break;
3753 case 17: strcat (buffer, " (DLGINCLUDE)"); break;
3754 case 19: strcat (buffer, " (PLUGPLAY)"); break;
3755 case 20: strcat (buffer, " (VXD)"); break;
3756 case 21: strcat (buffer, " (ANICURSOR)"); break;
3757 case 22: strcat (buffer, " (ANIICON)"); break;
3758 case 23: strcat (buffer, " (HTML)"); break;
3759 case 24: strcat (buffer, " (MANIFEST)"); break;
3760 case 240: strcat (buffer, " (DLGINIT)"); break;
3761 case 241: strcat (buffer, " (TOOLBAR)"); break;
3762 }
3763 }
3764 }
3765
3766 if (dir != NULL && dir->entry != NULL)
3767 {
3768 strcat (buffer, " name: ");
3769 if (dir->entry->is_name)
3770 rsrc_print_name (buffer + strlen (buffer), dir->entry->name_id.name);
3771 else
3772 {
3773 unsigned int id = dir->entry->name_id.id;
3774
3775 sprintf (buffer + strlen (buffer), "%x", id);
3776
3777 if (is_string)
3778 sprintf (buffer + strlen (buffer), " (resource id range: %d - %d)",
3779 (id - 1) << 4, (id << 4) - 1);
3780 }
3781 }
3782
3783 if (entry != NULL)
3784 {
3785 strcat (buffer, " lang: ");
3786
3787 if (entry->is_name)
3788 rsrc_print_name (buffer + strlen (buffer), entry->name_id.name);
3789 else
3790 sprintf (buffer + strlen (buffer), "%x", entry->name_id.id);
3791 }
3792
3793 return buffer;
3794}
3795
3796/* *sigh* Windows resource strings are special. Only the top 28-bits of
3797 their ID is stored in the NAME entry. The bottom four bits are used as
3798 an index into unicode string table that makes up the data of the leaf.
3799 So identical type-name-lang string resources may not actually be
3800 identical at all.
3801
3802 This function is called when we have detected two string resources with
3803 match top-28-bit IDs. We have to scan the string tables inside the leaves
3804 and discover if there are any real collisions. If there are then we report
9373215c
PM
3805 them and return FALSE. Otherwise we copy any strings from B into A and
3806 then return TRUE. */
5879bb8f
NC
3807
3808static bfd_boolean
3809rsrc_merge_string_entries (rsrc_entry * a ATTRIBUTE_UNUSED,
3810 rsrc_entry * b ATTRIBUTE_UNUSED)
3811{
3812 unsigned int copy_needed = 0;
3813 unsigned int i;
9373215c
PM
3814 bfd_byte * astring;
3815 bfd_byte * bstring;
3816 bfd_byte * new_data;
3817 bfd_byte * nstring;
5879bb8f
NC
3818
3819 /* Step one: Find out what we have to do. */
3820 BFD_ASSERT (! a->is_dir);
9373215c 3821 astring = a->value.leaf->data;
5879bb8f
NC
3822
3823 BFD_ASSERT (! b->is_dir);
9373215c 3824 bstring = b->value.leaf->data;
5879bb8f
NC
3825
3826 for (i = 0; i < 16; i++)
3827 {
3828 unsigned int alen = astring[0] + (astring[1] << 8);
3829 unsigned int blen = bstring[0] + (bstring[1] << 8);
3830
3831 if (alen == 0)
3832 {
3833 copy_needed += blen * 2;
3834 }
3835 else if (blen == 0)
3836 ;
3837 else if (alen != blen)
3838 /* FIXME: Should we continue the loop in order to report other duplicates ? */
3839 break;
3840 /* alen == blen != 0. We might have two identical strings. If so we
3841 can ignore the second one. There is no need for wchar_t vs UTF-16
3842 theatrics here - we are only interested in (case sensitive) equality. */
3843 else if (memcmp (astring + 2, bstring + 2, alen * 2) != 0)
3844 break;
3845
3846 astring += (alen + 1) * 2;
3847 bstring += (blen + 1) * 2;
3848 }
3849
3850 if (i != 16)
3851 {
3852 if (a->parent != NULL
3853 && a->parent->entry != NULL
535b785f 3854 && !a->parent->entry->is_name)
5879bb8f
NC
3855 _bfd_error_handler (_(".rsrc merge failure: duplicate string resource: %d"),
3856 ((a->parent->entry->name_id.id - 1) << 4) + i);
3857 return FALSE;
3858 }
3859
3860 if (copy_needed == 0)
3861 return TRUE;
3862
3863 /* If we reach here then A and B must both have non-colliding strings.
3864 (We never get string resources with fully empty string tables).
3865 We need to allocate an extra COPY_NEEDED bytes in A and then bring
3866 in B's strings. */
9373215c 3867 new_data = bfd_malloc (a->value.leaf->size + copy_needed);
5879bb8f
NC
3868 if (new_data == NULL)
3869 return FALSE;
3870
9373215c 3871 nstring = new_data;
5879bb8f
NC
3872 astring = a->value.leaf->data;
3873 bstring = b->value.leaf->data;
3874
3875 for (i = 0; i < 16; i++)
3876 {
3877 unsigned int alen = astring[0] + (astring[1] << 8);
3878 unsigned int blen = bstring[0] + (bstring[1] << 8);
3879
3880 if (alen != 0)
3881 {
3882 memcpy (nstring, astring, (alen + 1) * 2);
3883 nstring += (alen + 1) * 2;
3884 }
3885 else if (blen != 0)
3886 {
3887 memcpy (nstring, bstring, (blen + 1) * 2);
3888 nstring += (blen + 1) * 2;
3889 }
3890 else
3891 {
3892 * nstring++ = 0;
3893 * nstring++ = 0;
3894 }
9373215c 3895
5879bb8f
NC
3896 astring += (alen + 1) * 2;
3897 bstring += (blen + 1) * 2;
3898 }
3899
3900 BFD_ASSERT (nstring - new_data == (signed) (a->value.leaf->size + copy_needed));
9373215c 3901
5879bb8f
NC
3902 free (a->value.leaf->data);
3903 a->value.leaf->data = new_data;
3904 a->value.leaf->size += copy_needed;
3905
3906 return TRUE;
3907}
3908
3909static void rsrc_merge (rsrc_entry *, rsrc_entry *);
3910
3911/* Sort the entries in given part of the directory.
3912 We use an old fashioned bubble sort because we are dealing
9373215c 3913 with lists and we want to handle matches specially. */
5879bb8f
NC
3914
3915static void
3916rsrc_sort_entries (rsrc_dir_chain * chain,
3917 bfd_boolean is_name,
3918 rsrc_directory * dir)
3919{
3920 rsrc_entry * entry;
3921 rsrc_entry * next;
3922 rsrc_entry ** points_to_entry;
3923 bfd_boolean swapped;
3924
3925 if (chain->num_entries < 2)
3926 return;
3927
3928 do
3929 {
3930 swapped = FALSE;
3931 points_to_entry = & chain->first_entry;
3932 entry = * points_to_entry;
3933 next = entry->next_entry;
3934
3935 do
3936 {
3937 signed int cmp = rsrc_cmp (is_name, entry, next);
3938
3939 if (cmp > 0)
3940 {
3941 entry->next_entry = next->next_entry;
3942 next->next_entry = entry;
3943 * points_to_entry = next;
3944 points_to_entry = & next->next_entry;
3945 next = entry->next_entry;
3946 swapped = TRUE;
3947 }
3948 else if (cmp == 0)
3949 {
3950 if (entry->is_dir && next->is_dir)
3951 {
3952 /* When we encounter identical directory entries we have to
3953 merge them together. The exception to this rule is for
3954 resource manifests - there can only be one of these,
3955 even if they differ in language. Zero-language manifests
3956 are assumed to be default manifests (provided by the
3714081c 3957 Cygwin/MinGW build system) and these can be silently dropped,
5879bb8f
NC
3958 unless that would reduce the number of manifests to zero.
3959 There should only ever be one non-zero lang manifest -
3960 if there are more it is an error. A non-zero lang
3961 manifest takes precedence over a default manifest. */
535b785f 3962 if (!entry->is_name
5879bb8f
NC
3963 && entry->name_id.id == 1
3964 && dir != NULL
3965 && dir->entry != NULL
535b785f 3966 && !dir->entry->is_name
5879bb8f
NC
3967 && dir->entry->name_id.id == 0x18)
3968 {
3969 if (next->value.directory->names.num_entries == 0
3970 && next->value.directory->ids.num_entries == 1
535b785f 3971 && !next->value.directory->ids.first_entry->is_name
5879bb8f
NC
3972 && next->value.directory->ids.first_entry->name_id.id == 0)
3973 /* Fall through so that NEXT is dropped. */
3974 ;
3975 else if (entry->value.directory->names.num_entries == 0
3976 && entry->value.directory->ids.num_entries == 1
535b785f 3977 && !entry->value.directory->ids.first_entry->is_name
5879bb8f
NC
3978 && entry->value.directory->ids.first_entry->name_id.id == 0)
3979 {
3980 /* Swap ENTRY and NEXT. Then fall through so that the old ENTRY is dropped. */
3981 entry->next_entry = next->next_entry;
3982 next->next_entry = entry;
3983 * points_to_entry = next;
3984 points_to_entry = & next->next_entry;
3985 next = entry->next_entry;
3986 swapped = TRUE;
3987 }
3988 else
3989 {
3990 _bfd_error_handler (_(".rsrc merge failure: multiple non-default manifests"));
3991 bfd_set_error (bfd_error_file_truncated);
3992 return;
3993 }
9373215c 3994
5879bb8f
NC
3995 /* Unhook NEXT from the chain. */
3996 /* FIXME: memory loss here. */
3997 entry->next_entry = next->next_entry;
3998 chain->num_entries --;
3999 if (chain->num_entries < 2)
4000 return;
4001 next = next->next_entry;
4002 }
4003 else
4004 rsrc_merge (entry, next);
4005 }
4006 else if (entry->is_dir != next->is_dir)
4007 {
4008 _bfd_error_handler (_(".rsrc merge failure: a directory matches a leaf"));
4009 bfd_set_error (bfd_error_file_truncated);
4010 return;
4011 }
4012 else
4013 {
4014 /* Otherwise with identical leaves we issue an error
4015 message - because there should never be duplicates.
4016 The exception is Type 18/Name 1/Lang 0 which is the
4017 defaul manifest - this can just be dropped. */
535b785f 4018 if (!entry->is_name
5879bb8f
NC
4019 && entry->name_id.id == 0
4020 && dir != NULL
4021 && dir->entry != NULL
535b785f 4022 && !dir->entry->is_name
5879bb8f
NC
4023 && dir->entry->name_id.id == 1
4024 && dir->entry->parent != NULL
4025 && dir->entry->parent->entry != NULL
535b785f 4026 && !dir->entry->parent->entry->is_name
5879bb8f
NC
4027 && dir->entry->parent->entry->name_id.id == 0x18 /* RT_MANIFEST */)
4028 ;
4029 else if (dir != NULL
4030 && dir->entry != NULL
4031 && dir->entry->parent != NULL
4032 && dir->entry->parent->entry != NULL
535b785f 4033 && !dir->entry->parent->entry->is_name
5879bb8f
NC
4034 && dir->entry->parent->entry->name_id.id == 0x6 /* RT_STRING */)
4035 {
4036 /* Strings need special handling. */
4037 if (! rsrc_merge_string_entries (entry, next))
4038 {
4039 /* _bfd_error_handler should have been called inside merge_strings. */
4040 bfd_set_error (bfd_error_file_truncated);
4041 return;
4042 }
4043 }
4044 else
4045 {
4046 if (dir == NULL
4047 || dir->entry == NULL
4048 || dir->entry->parent == NULL
4049 || dir->entry->parent->entry == NULL)
4050 _bfd_error_handler (_(".rsrc merge failure: duplicate leaf"));
4051 else
4052 _bfd_error_handler (_(".rsrc merge failure: duplicate leaf: %s"),
4053 rsrc_resource_name (entry, dir));
4054 bfd_set_error (bfd_error_file_truncated);
4055 return;
4056 }
4057 }
4058
4059 /* Unhook NEXT from the chain. */
4060 entry->next_entry = next->next_entry;
4061 chain->num_entries --;
4062 if (chain->num_entries < 2)
4063 return;
4064 next = next->next_entry;
4065 }
4066 else
4067 {
4068 points_to_entry = & entry->next_entry;
4069 entry = next;
4070 next = next->next_entry;
4071 }
4072 }
4073 while (next);
4074
4075 chain->last_entry = entry;
4076 }
4077 while (swapped);
4078}
4079
4080/* Attach B's chain onto A. */
4081static void
9373215c 4082rsrc_attach_chain (rsrc_dir_chain * achain, rsrc_dir_chain * bchain)
5879bb8f
NC
4083{
4084 if (bchain->num_entries == 0)
4085 return;
4086
4087 achain->num_entries += bchain->num_entries;
4088
4089 if (achain->first_entry == NULL)
4090 {
4091 achain->first_entry = bchain->first_entry;
4092 achain->last_entry = bchain->last_entry;
4093 }
4094 else
4095 {
4096 achain->last_entry->next_entry = bchain->first_entry;
4097 achain->last_entry = bchain->last_entry;
4098 }
9373215c 4099
5879bb8f
NC
4100 bchain->num_entries = 0;
4101 bchain->first_entry = bchain->last_entry = NULL;
4102}
4103
4104static void
4105rsrc_merge (struct rsrc_entry * a, struct rsrc_entry * b)
4106{
9373215c
PM
4107 rsrc_directory * adir;
4108 rsrc_directory * bdir;
4109
5879bb8f
NC
4110 BFD_ASSERT (a->is_dir);
4111 BFD_ASSERT (b->is_dir);
4112
9373215c
PM
4113 adir = a->value.directory;
4114 bdir = b->value.directory;
4115
5879bb8f
NC
4116 if (adir->characteristics != bdir->characteristics)
4117 {
59d08d6c 4118 _bfd_error_handler (_(".rsrc merge failure: dirs with differing characteristics"));
5879bb8f
NC
4119 bfd_set_error (bfd_error_file_truncated);
4120 return;
4121 }
9373215c 4122
5879bb8f
NC
4123 if (adir->major != bdir->major || adir->minor != bdir->minor)
4124 {
59d08d6c 4125 _bfd_error_handler (_(".rsrc merge failure: differing directory versions"));
5879bb8f
NC
4126 bfd_set_error (bfd_error_file_truncated);
4127 return;
4128 }
4129
4130 /* Attach B's name chain to A. */
4131 rsrc_attach_chain (& adir->names, & bdir->names);
4132
4133 /* Attach B's ID chain to A. */
4134 rsrc_attach_chain (& adir->ids, & bdir->ids);
4135
4136 /* Now sort A's entries. */
4137 rsrc_sort_entries (& adir->names, TRUE, adir);
4138 rsrc_sort_entries (& adir->ids, FALSE, adir);
4139}
4140
4141/* Check the .rsrc section. If it contains multiple concatenated
4142 resources then we must merge them properly. Otherwise Windows
4143 will ignore all but the first set. */
4144
4145static void
4146rsrc_process_section (bfd * abfd,
4147 struct coff_final_link_info * pfinfo)
4148{
9373215c 4149 rsrc_directory new_table;
07d6d2b8
AM
4150 bfd_size_type size;
4151 asection * sec;
9373215c 4152 pe_data_type * pe;
07d6d2b8
AM
4153 bfd_vma rva_bias;
4154 bfd_byte * data;
4155 bfd_byte * datastart;
4156 bfd_byte * dataend;
4157 bfd_byte * new_data;
4158 unsigned int num_resource_sets;
9373215c
PM
4159 rsrc_directory * type_tables;
4160 rsrc_write_data write_data;
07d6d2b8
AM
4161 unsigned int indx;
4162 bfd * input;
4163 unsigned int num_input_rsrc = 0;
4164 unsigned int max_num_input_rsrc = 4;
4165 ptrdiff_t * rsrc_sizes = NULL;
5879bb8f
NC
4166
4167 new_table.names.num_entries = 0;
4168 new_table.ids.num_entries = 0;
9373215c 4169
5879bb8f
NC
4170 sec = bfd_get_section_by_name (abfd, ".rsrc");
4171 if (sec == NULL || (size = sec->rawsize) == 0)
4172 return;
4173
9373215c 4174 pe = pe_data (abfd);
5879bb8f
NC
4175 if (pe == NULL)
4176 return;
4177
5879bb8f
NC
4178 rva_bias = sec->vma - pe->pe_opthdr.ImageBase;
4179
9373215c 4180 data = bfd_malloc (size);
5879bb8f
NC
4181 if (data == NULL)
4182 return;
c32abae8 4183
9373215c 4184 datastart = data;
5879bb8f
NC
4185
4186 if (! bfd_get_section_contents (abfd, sec, data, 0, size))
4187 goto end;
4188
6caf7111
NC
4189 /* Step zero: Scan the input bfds looking for .rsrc sections and record
4190 their lengths. Note - we rely upon the fact that the linker script
4191 does *not* sort the input .rsrc sections, so that the order in the
4192 linkinfo list matches the order in the output .rsrc section.
4193
4194 We need to know the lengths because each input .rsrc section has padding
4195 at the end of a variable amount. (It does not appear to be based upon
4196 the section alignment or the file alignment). We need to skip any
4197 padding bytes when parsing the input .rsrc sections. */
4198 rsrc_sizes = bfd_malloc (max_num_input_rsrc * sizeof * rsrc_sizes);
4199 if (rsrc_sizes == NULL)
4200 goto end;
4201
4202 for (input = pfinfo->info->input_bfds;
4203 input != NULL;
c72f2fb2 4204 input = input->link.next)
6caf7111
NC
4205 {
4206 asection * rsrc_sec = bfd_get_section_by_name (input, ".rsrc");
4207
9ac47a43
TS
4208 /* PR 18372 - skip discarded .rsrc sections. */
4209 if (rsrc_sec != NULL && !discarded_section (rsrc_sec))
6caf7111
NC
4210 {
4211 if (num_input_rsrc == max_num_input_rsrc)
4212 {
4213 max_num_input_rsrc += 10;
4214 rsrc_sizes = bfd_realloc (rsrc_sizes, max_num_input_rsrc
4215 * sizeof * rsrc_sizes);
4216 if (rsrc_sizes == NULL)
4217 goto end;
4218 }
4219
4220 BFD_ASSERT (rsrc_sec->size > 0);
4221 rsrc_sizes [num_input_rsrc ++] = rsrc_sec->size;
4222 }
4223 }
4224
4225 if (num_input_rsrc < 2)
4226 goto end;
61e2488c 4227
5879bb8f
NC
4228 /* Step one: Walk the section, computing the size of the tables,
4229 leaves and data and decide if we need to do anything. */
1d63324c 4230 dataend = data + size;
9373215c 4231 num_resource_sets = 0;
5879bb8f
NC
4232
4233 while (data < dataend)
4234 {
4235 bfd_byte * p = data;
4236
4237 data = rsrc_count_directory (abfd, data, data, dataend, rva_bias);
1d63324c 4238
5879bb8f
NC
4239 if (data > dataend)
4240 {
4241 /* Corrupted .rsrc section - cannot merge. */
871b3ab2 4242 _bfd_error_handler (_("%pB: .rsrc merge failure: corrupt .rsrc section"),
dae82561 4243 abfd);
5879bb8f
NC
4244 bfd_set_error (bfd_error_file_truncated);
4245 goto end;
4246 }
4247
6caf7111
NC
4248 if ((data - p) > rsrc_sizes [num_resource_sets])
4249 {
871b3ab2 4250 _bfd_error_handler (_("%pB: .rsrc merge failure: unexpected .rsrc size"),
dae82561 4251 abfd);
6caf7111
NC
4252 bfd_set_error (bfd_error_file_truncated);
4253 goto end;
4254 }
4255 /* FIXME: Should we add a check for "data - p" being much smaller
4256 than rsrc_sizes[num_resource_sets] ? */
4257
4258 data = p + rsrc_sizes[num_resource_sets];
5879bb8f 4259 rva_bias += data - p;
5879bb8f
NC
4260 ++ num_resource_sets;
4261 }
6caf7111 4262 BFD_ASSERT (num_resource_sets == num_input_rsrc);
5879bb8f
NC
4263
4264 /* Step two: Walk the data again, building trees of the resources. */
4265 data = datastart;
4266 rva_bias = sec->vma - pe->pe_opthdr.ImageBase;
4267
9373215c 4268 type_tables = bfd_malloc (num_resource_sets * sizeof * type_tables);
5879bb8f
NC
4269 if (type_tables == NULL)
4270 goto end;
4271
9373215c 4272 indx = 0;
5879bb8f
NC
4273 while (data < dataend)
4274 {
4275 bfd_byte * p = data;
4276
6caf7111 4277 (void) rsrc_parse_directory (abfd, type_tables + indx, data, data,
9373215c 4278 dataend, rva_bias, NULL);
6caf7111 4279 data = p + rsrc_sizes[indx];
5879bb8f 4280 rva_bias += data - p;
6caf7111 4281 ++ indx;
5879bb8f 4282 }
337e86d7 4283 BFD_ASSERT (indx == num_resource_sets);
9373215c 4284
5879bb8f 4285 /* Step three: Merge the top level tables (there can be only one).
9373215c 4286
5879bb8f 4287 We must ensure that the merged entries are in ascending order.
9373215c 4288
5879bb8f
NC
4289 We also thread the top level table entries from the old tree onto
4290 the new table, so that they can be pulled off later. */
4291
4292 /* FIXME: Should we verify that all type tables are the same ? */
4293 new_table.characteristics = type_tables[0].characteristics;
07d6d2b8
AM
4294 new_table.time = type_tables[0].time;
4295 new_table.major = type_tables[0].major;
4296 new_table.minor = type_tables[0].minor;
5879bb8f
NC
4297
4298 /* Chain the NAME entries onto the table. */
4299 new_table.names.first_entry = NULL;
4300 new_table.names.last_entry = NULL;
4301
337e86d7
L
4302 for (indx = 0; indx < num_resource_sets; indx++)
4303 rsrc_attach_chain (& new_table.names, & type_tables[indx].names);
5879bb8f
NC
4304
4305 rsrc_sort_entries (& new_table.names, TRUE, & new_table);
9373215c 4306
5879bb8f
NC
4307 /* Chain the ID entries onto the table. */
4308 new_table.ids.first_entry = NULL;
4309 new_table.ids.last_entry = NULL;
4310
337e86d7
L
4311 for (indx = 0; indx < num_resource_sets; indx++)
4312 rsrc_attach_chain (& new_table.ids, & type_tables[indx].ids);
5879bb8f
NC
4313
4314 rsrc_sort_entries (& new_table.ids, FALSE, & new_table);
4315
4316 /* Step four: Create new contents for the .rsrc section. */
3714081c
NC
4317 /* Step four point one: Compute the size of each region of the .rsrc section.
4318 We do this now, rather than earlier, as the merging above may have dropped
4319 some entries. */
4320 sizeof_leaves = sizeof_strings = sizeof_tables_and_entries = 0;
4321 rsrc_compute_region_sizes (& new_table);
4322 /* We increment sizeof_strings to make sure that resource data
4323 starts on an 8-byte boundary. FIXME: Is this correct ? */
4324 sizeof_strings = (sizeof_strings + 7) & ~ 7;
4325
c32abae8 4326 new_data = bfd_zalloc (abfd, size);
5879bb8f
NC
4327 if (new_data == NULL)
4328 goto end;
4329
07d6d2b8
AM
4330 write_data.abfd = abfd;
4331 write_data.datastart = new_data;
4332 write_data.next_table = new_data;
4333 write_data.next_leaf = new_data + sizeof_tables_and_entries;
5879bb8f 4334 write_data.next_string = write_data.next_leaf + sizeof_leaves;
07d6d2b8
AM
4335 write_data.next_data = write_data.next_string + sizeof_strings;
4336 write_data.rva_bias = sec->vma - pe->pe_opthdr.ImageBase;
5879bb8f
NC
4337
4338 rsrc_write_directory (& write_data, & new_table);
4339
4340 /* Step five: Replace the old contents with the new.
ec8f7688
JT
4341 We don't recompute the size as it's too late here to shrink section.
4342 See PR ld/20193 for more details. */
5879bb8f
NC
4343 bfd_set_section_contents (pfinfo->output_bfd, sec, new_data, 0, size);
4344 sec->size = sec->rawsize = size;
9373215c 4345
5879bb8f 4346 end:
3714081c 4347 /* Step six: Free all the memory that we have used. */
5879bb8f
NC
4348 /* FIXME: Free the resource tree, if we have one. */
4349 free (datastart);
6caf7111 4350 free (rsrc_sizes);
5879bb8f 4351}
5174d0fb 4352
2fbadf2c
ILT
4353/* Handle the .idata section and other things that need symbol table
4354 access. */
4355
b34976b6 4356bfd_boolean
7920ce38 4357_bfd_XXi_final_link_postscript (bfd * abfd, struct coff_final_link_info *pfinfo)
2fbadf2c
ILT
4358{
4359 struct coff_link_hash_entry *h1;
4360 struct bfd_link_info *info = pfinfo->info;
4e22f78d 4361 bfd_boolean result = TRUE;
2fbadf2c
ILT
4362
4363 /* There are a few fields that need to be filled in now while we
4364 have symbol table access.
4365
4366 The .idata subsections aren't directly available as sections, but
4367 they are in the symbol table, so get them from there. */
4368
4369 /* The import directory. This is the address of .idata$2, with size
4370 of .idata$2 + .idata$3. */
4371 h1 = coff_link_hash_lookup (coff_hash_table (info),
b34976b6 4372 ".idata$2", FALSE, FALSE, TRUE);
2fbadf2c
ILT
4373 if (h1 != NULL)
4374 {
4e1fc599 4375 /* PR ld/2729: We cannot rely upon all the output sections having been
4e22f78d
NC
4376 created properly, so check before referencing them. Issue a warning
4377 message for any sections tht could not be found. */
b92997d6
AM
4378 if ((h1->root.type == bfd_link_hash_defined
4379 || h1->root.type == bfd_link_hash_defweak)
4380 && h1->root.u.def.section != NULL
4e22f78d 4381 && h1->root.u.def.section->output_section != NULL)
6c73cbb1 4382 pe_data (abfd)->pe_opthdr.DataDirectory[PE_IMPORT_TABLE].VirtualAddress =
4e22f78d
NC
4383 (h1->root.u.def.value
4384 + h1->root.u.def.section->output_section->vma
4385 + h1->root.u.def.section->output_offset);
4386 else
4387 {
4388 _bfd_error_handler
871b3ab2 4389 (_("%pB: unable to fill in DataDictionary[1] because .idata$2 is missing"),
4e22f78d
NC
4390 abfd);
4391 result = FALSE;
4392 }
4393
2fbadf2c 4394 h1 = coff_link_hash_lookup (coff_hash_table (info),
b34976b6 4395 ".idata$4", FALSE, FALSE, TRUE);
4e22f78d 4396 if (h1 != NULL
b92997d6
AM
4397 && (h1->root.type == bfd_link_hash_defined
4398 || h1->root.type == bfd_link_hash_defweak)
4e22f78d
NC
4399 && h1->root.u.def.section != NULL
4400 && h1->root.u.def.section->output_section != NULL)
6c73cbb1 4401 pe_data (abfd)->pe_opthdr.DataDirectory[PE_IMPORT_TABLE].Size =
4e22f78d
NC
4402 ((h1->root.u.def.value
4403 + h1->root.u.def.section->output_section->vma
4404 + h1->root.u.def.section->output_offset)
6c73cbb1 4405 - pe_data (abfd)->pe_opthdr.DataDirectory[PE_IMPORT_TABLE].VirtualAddress);
4e22f78d
NC
4406 else
4407 {
4408 _bfd_error_handler
871b3ab2 4409 (_("%pB: unable to fill in DataDictionary[1] because .idata$4 is missing"),
4e22f78d
NC
4410 abfd);
4411 result = FALSE;
4412 }
2fbadf2c
ILT
4413
4414 /* The import address table. This is the size/address of
07d6d2b8 4415 .idata$5. */
2fbadf2c 4416 h1 = coff_link_hash_lookup (coff_hash_table (info),
b34976b6 4417 ".idata$5", FALSE, FALSE, TRUE);
4e22f78d 4418 if (h1 != NULL
b92997d6
AM
4419 && (h1->root.type == bfd_link_hash_defined
4420 || h1->root.type == bfd_link_hash_defweak)
4e22f78d
NC
4421 && h1->root.u.def.section != NULL
4422 && h1->root.u.def.section->output_section != NULL)
6c73cbb1 4423 pe_data (abfd)->pe_opthdr.DataDirectory[PE_IMPORT_ADDRESS_TABLE].VirtualAddress =
4e22f78d
NC
4424 (h1->root.u.def.value
4425 + h1->root.u.def.section->output_section->vma
4426 + h1->root.u.def.section->output_offset);
4427 else
4428 {
4429 _bfd_error_handler
871b3ab2 4430 (_("%pB: unable to fill in DataDictionary[12] because .idata$5 is missing"),
4e22f78d
NC
4431 abfd);
4432 result = FALSE;
4433 }
4434
2fbadf2c 4435 h1 = coff_link_hash_lookup (coff_hash_table (info),
b34976b6 4436 ".idata$6", FALSE, FALSE, TRUE);
4e22f78d 4437 if (h1 != NULL
b92997d6
AM
4438 && (h1->root.type == bfd_link_hash_defined
4439 || h1->root.type == bfd_link_hash_defweak)
4e22f78d
NC
4440 && h1->root.u.def.section != NULL
4441 && h1->root.u.def.section->output_section != NULL)
6c73cbb1 4442 pe_data (abfd)->pe_opthdr.DataDirectory[PE_IMPORT_ADDRESS_TABLE].Size =
4e22f78d
NC
4443 ((h1->root.u.def.value
4444 + h1->root.u.def.section->output_section->vma
4445 + h1->root.u.def.section->output_offset)
4e1fc599 4446 - pe_data (abfd)->pe_opthdr.DataDirectory[PE_IMPORT_ADDRESS_TABLE].VirtualAddress);
4e22f78d
NC
4447 else
4448 {
4449 _bfd_error_handler
871b3ab2 4450 (_("%pB: unable to fill in DataDictionary[PE_IMPORT_ADDRESS_TABLE (12)] because .idata$6 is missing"),
4e22f78d
NC
4451 abfd);
4452 result = FALSE;
4453 }
2fbadf2c 4454 }
cb2f80e6
KT
4455 else
4456 {
4457 h1 = coff_link_hash_lookup (coff_hash_table (info),
4458 "__IAT_start__", FALSE, FALSE, TRUE);
4459 if (h1 != NULL
4460 && (h1->root.type == bfd_link_hash_defined
4461 || h1->root.type == bfd_link_hash_defweak)
4462 && h1->root.u.def.section != NULL
4463 && h1->root.u.def.section->output_section != NULL)
4464 {
4465 bfd_vma iat_va;
4466
4467 iat_va =
4468 (h1->root.u.def.value
4469 + h1->root.u.def.section->output_section->vma
4470 + h1->root.u.def.section->output_offset);
4471
4472 h1 = coff_link_hash_lookup (coff_hash_table (info),
4473 "__IAT_end__", FALSE, FALSE, TRUE);
4474 if (h1 != NULL
4475 && (h1->root.type == bfd_link_hash_defined
4476 || h1->root.type == bfd_link_hash_defweak)
4477 && h1->root.u.def.section != NULL
4478 && h1->root.u.def.section->output_section != NULL)
4479 {
4480 pe_data (abfd)->pe_opthdr.DataDirectory[PE_IMPORT_ADDRESS_TABLE].Size =
4481 ((h1->root.u.def.value
4482 + h1->root.u.def.section->output_section->vma
4483 + h1->root.u.def.section->output_offset)
4484 - iat_va);
4485 if (pe_data (abfd)->pe_opthdr.DataDirectory[PE_IMPORT_ADDRESS_TABLE].Size != 0)
4486 pe_data (abfd)->pe_opthdr.DataDirectory[PE_IMPORT_ADDRESS_TABLE].VirtualAddress =
4487 iat_va - pe_data (abfd)->pe_opthdr.ImageBase;
4488 }
4489 else
4490 {
4491 _bfd_error_handler
871b3ab2 4492 (_("%pB: unable to fill in DataDictionary[PE_IMPORT_ADDRESS_TABLE(12)]"
cb2f80e6
KT
4493 " because .idata$6 is missing"), abfd);
4494 result = FALSE;
4495 }
07d6d2b8 4496 }
cb2f80e6 4497 }
ca6dee30
NC
4498
4499 h1 = coff_link_hash_lookup (coff_hash_table (info),
61e2488c 4500 (bfd_get_symbol_leading_char (abfd) != 0
c91a930c
KT
4501 ? "__tls_used" : "_tls_used"),
4502 FALSE, FALSE, TRUE);
ca6dee30
NC
4503 if (h1 != NULL)
4504 {
b92997d6
AM
4505 if ((h1->root.type == bfd_link_hash_defined
4506 || h1->root.type == bfd_link_hash_defweak)
4507 && h1->root.u.def.section != NULL
4e22f78d 4508 && h1->root.u.def.section->output_section != NULL)
6c73cbb1 4509 pe_data (abfd)->pe_opthdr.DataDirectory[PE_TLS_TABLE].VirtualAddress =
4e22f78d
NC
4510 (h1->root.u.def.value
4511 + h1->root.u.def.section->output_section->vma
4512 + h1->root.u.def.section->output_offset
4513 - pe_data (abfd)->pe_opthdr.ImageBase);
4514 else
4515 {
4516 _bfd_error_handler
871b3ab2 4517 (_("%pB: unable to fill in DataDictionary[9] because __tls_used is missing"),
4e22f78d
NC
4518 abfd);
4519 result = FALSE;
4520 }
bc2b2990
PM
4521 /* According to PECOFF sepcifications by Microsoft version 8.2
4522 the TLS data directory consists of 4 pointers, followed
4523 by two 4-byte integer. This implies that the total size
68ffbac6 4524 is different for 32-bit and 64-bit executables. */
bc2b2990 4525#if !defined(COFF_WITH_pep) && !defined(COFF_WITH_pex64)
6c73cbb1 4526 pe_data (abfd)->pe_opthdr.DataDirectory[PE_TLS_TABLE].Size = 0x18;
bc2b2990
PM
4527#else
4528 pe_data (abfd)->pe_opthdr.DataDirectory[PE_TLS_TABLE].Size = 0x28;
4529#endif
ca6dee30
NC
4530 }
4531
5174d0fb
KT
4532/* If there is a .pdata section and we have linked pdata finally, we
4533 need to sort the entries ascending. */
4534#if !defined(COFF_WITH_pep) && defined(COFF_WITH_pex64)
4535 {
4536 asection *sec = bfd_get_section_by_name (abfd, ".pdata");
4537
4538 if (sec)
4539 {
21e68916
KT
4540 bfd_size_type x = sec->rawsize;
4541 bfd_byte *tmp_data = NULL;
5174d0fb 4542
21e68916
KT
4543 if (x)
4544 tmp_data = bfd_malloc (x);
4545
4546 if (tmp_data != NULL)
5174d0fb 4547 {
21e68916
KT
4548 if (bfd_get_section_contents (abfd, sec, tmp_data, 0, x))
4549 {
4550 qsort (tmp_data,
4551 (size_t) (x / 12),
4552 12, sort_x64_pdata);
4553 bfd_set_section_contents (pfinfo->output_bfd, sec,
4554 tmp_data, 0, x);
4555 }
4556 free (tmp_data);
5174d0fb 4557 }
86eafac0
NC
4558 else
4559 result = FALSE;
5174d0fb
KT
4560 }
4561 }
4562#endif
4563
5879bb8f
NC
4564 rsrc_process_section (abfd, pfinfo);
4565
2fbadf2c
ILT
4566 /* If we couldn't find idata$2, we either have an excessively
4567 trivial program or are in DEEP trouble; we have to assume trivial
4568 program.... */
4e22f78d 4569 return result;
2fbadf2c 4570}
This page took 1.595142 seconds and 4 git commands to generate.