* emultempl/pe.em (debug_section_p): New bfd_map_over_sections hook.
[binutils.git] / bfd / coff64-rs6000.c
blob776b6a22e2c3b578daa7b94f947745c940b5bceb
1 /* BFD back-end for IBM RS/6000 "XCOFF64" files.
2 Copyright 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
3 Free Software Foundation, Inc.
4 Written Clinton Popetz.
5 Contributed by Cygnus Support.
7 This file is part of BFD, the Binary File Descriptor library.
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 3 of the License, or
12 (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with this program; if not, write to the Free Software
21 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
22 MA 02110-1301, USA. */
24 #include "sysdep.h"
25 #include "bfd.h"
26 #include "bfdlink.h"
27 #include "libbfd.h"
28 #include "coff/internal.h"
29 #include "coff/xcoff.h"
30 #include "coff/rs6k64.h"
31 #include "libcoff.h"
32 #include "libxcoff.h"
34 #define GET_FILEHDR_SYMPTR H_GET_64
35 #define PUT_FILEHDR_SYMPTR H_PUT_64
36 #define GET_AOUTHDR_DATA_START H_GET_64
37 #define PUT_AOUTHDR_DATA_START H_PUT_64
38 #define GET_AOUTHDR_TEXT_START H_GET_64
39 #define PUT_AOUTHDR_TEXT_START H_PUT_64
40 #define GET_AOUTHDR_TSIZE H_GET_64
41 #define PUT_AOUTHDR_TSIZE H_PUT_64
42 #define GET_AOUTHDR_DSIZE H_GET_64
43 #define PUT_AOUTHDR_DSIZE H_PUT_64
44 #define GET_AOUTHDR_BSIZE H_GET_64
45 #define PUT_AOUTHDR_BSIZE H_PUT_64
46 #define GET_AOUTHDR_ENTRY H_GET_64
47 #define PUT_AOUTHDR_ENTRY H_PUT_64
48 #define GET_SCNHDR_PADDR H_GET_64
49 #define PUT_SCNHDR_PADDR H_PUT_64
50 #define GET_SCNHDR_VADDR H_GET_64
51 #define PUT_SCNHDR_VADDR H_PUT_64
52 #define GET_SCNHDR_SIZE H_GET_64
53 #define PUT_SCNHDR_SIZE H_PUT_64
54 #define GET_SCNHDR_SCNPTR H_GET_64
55 #define PUT_SCNHDR_SCNPTR H_PUT_64
56 #define GET_SCNHDR_RELPTR H_GET_64
57 #define PUT_SCNHDR_RELPTR H_PUT_64
58 #define GET_SCNHDR_LNNOPTR H_GET_64
59 #define PUT_SCNHDR_LNNOPTR H_PUT_64
60 #define GET_SCNHDR_NRELOC H_GET_32
61 #define MAX_SCNHDR_NRELOC 0xffffffff
62 #define PUT_SCNHDR_NRELOC H_PUT_32
63 #define GET_SCNHDR_NLNNO H_GET_32
64 #define MAX_SCNHDR_NLNNO 0xffffffff
65 #define PUT_SCNHDR_NLNNO H_PUT_32
66 #define GET_RELOC_VADDR H_GET_64
67 #define PUT_RELOC_VADDR H_PUT_64
69 #define COFF_FORCE_SYMBOLS_IN_STRINGS
70 #define COFF_DEBUG_STRING_WIDE_PREFIX
73 #define COFF_ADJUST_SCNHDR_OUT_POST(ABFD, INT, EXT) \
74 do \
75 { \
76 memset (((SCNHDR *) EXT)->s_pad, 0, \
77 sizeof (((SCNHDR *) EXT)->s_pad)); \
78 } \
79 while (0)
81 #define NO_COFF_LINENOS
83 #define coff_SWAP_lineno_in _bfd_xcoff64_swap_lineno_in
84 #define coff_SWAP_lineno_out _bfd_xcoff64_swap_lineno_out
86 static void _bfd_xcoff64_swap_lineno_in
87 PARAMS ((bfd *, PTR, PTR));
88 static unsigned int _bfd_xcoff64_swap_lineno_out
89 PARAMS ((bfd *, PTR, PTR));
90 static bfd_boolean _bfd_xcoff64_put_symbol_name
91 PARAMS ((bfd *, struct bfd_strtab_hash *, struct internal_syment *,
92 const char *));
93 static bfd_boolean _bfd_xcoff64_put_ldsymbol_name
94 PARAMS ((bfd *, struct xcoff_loader_info *, struct internal_ldsym *,
95 const char *));
96 static void _bfd_xcoff64_swap_sym_in
97 PARAMS ((bfd *, PTR, PTR));
98 static unsigned int _bfd_xcoff64_swap_sym_out
99 PARAMS ((bfd *, PTR, PTR));
100 static void _bfd_xcoff64_swap_aux_in
101 PARAMS ((bfd *, PTR, int, int, int, int, PTR));
102 static unsigned int _bfd_xcoff64_swap_aux_out
103 PARAMS ((bfd *, PTR, int, int, int, int, PTR));
104 static void xcoff64_swap_reloc_in
105 PARAMS ((bfd *, PTR, PTR));
106 static unsigned int xcoff64_swap_reloc_out
107 PARAMS ((bfd *, PTR, PTR));
108 extern bfd_boolean _bfd_xcoff_mkobject
109 PARAMS ((bfd *));
110 extern bfd_boolean _bfd_xcoff_copy_private_bfd_data
111 PARAMS ((bfd *, bfd *));
112 extern bfd_boolean _bfd_xcoff_is_local_label_name
113 PARAMS ((bfd *, const char *));
114 extern void xcoff64_rtype2howto
115 PARAMS ((arelent *, struct internal_reloc *));
116 extern reloc_howto_type * xcoff64_reloc_type_lookup
117 PARAMS ((bfd *, bfd_reloc_code_real_type));
118 extern bfd_boolean _bfd_xcoff_slurp_armap
119 PARAMS ((bfd *));
120 extern PTR _bfd_xcoff_read_ar_hdr
121 PARAMS ((bfd *));
122 extern bfd *_bfd_xcoff_openr_next_archived_file
123 PARAMS ((bfd *, bfd *));
124 extern int _bfd_xcoff_stat_arch_elt
125 PARAMS ((bfd *, struct stat *));
126 extern bfd_boolean _bfd_xcoff_write_armap
127 PARAMS ((bfd *, unsigned int, struct orl *, unsigned int, int));
128 extern bfd_boolean _bfd_xcoff_write_archive_contents
129 PARAMS ((bfd *));
130 extern int _bfd_xcoff_sizeof_headers
131 PARAMS ((bfd *, struct bfd_link_info *));
132 extern void _bfd_xcoff_swap_sym_in
133 PARAMS ((bfd *, PTR, PTR));
134 extern unsigned int _bfd_xcoff_swap_sym_out
135 PARAMS ((bfd *, PTR, PTR));
136 extern void _bfd_xcoff_swap_aux_in
137 PARAMS ((bfd *, PTR, int, int, int, int, PTR));
138 extern unsigned int _bfd_xcoff_swap_aux_out
139 PARAMS ((bfd *, PTR, int, int, int, int, PTR));
140 static void xcoff64_swap_ldhdr_in
141 PARAMS ((bfd *, const PTR, struct internal_ldhdr *));
142 static void xcoff64_swap_ldhdr_out
143 PARAMS ((bfd *, const struct internal_ldhdr *, PTR d));
144 static void xcoff64_swap_ldsym_in
145 PARAMS ((bfd *, const PTR, struct internal_ldsym *));
146 static void xcoff64_swap_ldsym_out
147 PARAMS ((bfd *, const struct internal_ldsym *, PTR d));
148 static void xcoff64_swap_ldrel_in
149 PARAMS ((bfd *, const PTR, struct internal_ldrel *));
150 static void xcoff64_swap_ldrel_out
151 PARAMS ((bfd *, const struct internal_ldrel *, PTR d));
152 static bfd_boolean xcoff64_write_object_contents
153 PARAMS ((bfd *));
154 static bfd_boolean xcoff64_ppc_relocate_section
155 PARAMS ((bfd *, struct bfd_link_info *, bfd *, asection *, bfd_byte *,
156 struct internal_reloc *, struct internal_syment *,
157 asection **));
158 static bfd_boolean xcoff64_slurp_armap
159 PARAMS ((bfd *));
160 static const bfd_target *xcoff64_archive_p
161 PARAMS ((bfd *));
162 static bfd *xcoff64_openr_next_archived_file
163 PARAMS ((bfd *, bfd *));
164 static int xcoff64_sizeof_headers
165 PARAMS ((bfd *, struct bfd_link_info *));
166 static asection *xcoff64_create_csect_from_smclas
167 PARAMS ((bfd *, union internal_auxent *, const char *));
168 static bfd_boolean xcoff64_is_lineno_count_overflow
169 PARAMS ((bfd *, bfd_vma));
170 static bfd_boolean xcoff64_is_reloc_count_overflow
171 PARAMS ((bfd *, bfd_vma));
172 static bfd_vma xcoff64_loader_symbol_offset
173 PARAMS ((bfd *, struct internal_ldhdr *));
174 static bfd_vma xcoff64_loader_reloc_offset
175 PARAMS ((bfd *, struct internal_ldhdr *));
176 static bfd_boolean xcoff64_generate_rtinit
177 PARAMS ((bfd *, const char *, const char *, bfd_boolean));
178 static bfd_boolean xcoff64_bad_format_hook
179 PARAMS ((bfd *, PTR ));
181 /* Relocation functions */
182 static bfd_boolean xcoff64_reloc_type_br
183 PARAMS ((XCOFF_RELOC_FUNCTION_ARGS));
185 bfd_boolean (*xcoff64_calculate_relocation[XCOFF_MAX_CALCULATE_RELOCATION])
186 PARAMS ((XCOFF_RELOC_FUNCTION_ARGS)) =
188 xcoff_reloc_type_pos, /* R_POS (0x00) */
189 xcoff_reloc_type_neg, /* R_NEG (0x01) */
190 xcoff_reloc_type_rel, /* R_REL (0x02) */
191 xcoff_reloc_type_toc, /* R_TOC (0x03) */
192 xcoff_reloc_type_fail, /* R_RTB (0x04) */
193 xcoff_reloc_type_toc, /* R_GL (0x05) */
194 xcoff_reloc_type_toc, /* R_TCL (0x06) */
195 xcoff_reloc_type_fail, /* (0x07) */
196 xcoff_reloc_type_ba, /* R_BA (0x08) */
197 xcoff_reloc_type_fail, /* (0x09) */
198 xcoff64_reloc_type_br, /* R_BR (0x0a) */
199 xcoff_reloc_type_fail, /* (0x0b) */
200 xcoff_reloc_type_pos, /* R_RL (0x0c) */
201 xcoff_reloc_type_pos, /* R_RLA (0x0d) */
202 xcoff_reloc_type_fail, /* (0x0e) */
203 xcoff_reloc_type_noop, /* R_REF (0x0f) */
204 xcoff_reloc_type_fail, /* (0x10) */
205 xcoff_reloc_type_fail, /* (0x11) */
206 xcoff_reloc_type_toc, /* R_TRL (0x12) */
207 xcoff_reloc_type_toc, /* R_TRLA (0x13) */
208 xcoff_reloc_type_fail, /* R_RRTBI (0x14) */
209 xcoff_reloc_type_fail, /* R_RRTBA (0x15) */
210 xcoff_reloc_type_ba, /* R_CAI (0x16) */
211 xcoff_reloc_type_crel, /* R_CREL (0x17) */
212 xcoff_reloc_type_ba, /* R_RBA (0x18) */
213 xcoff_reloc_type_ba, /* R_RBAC (0x19) */
214 xcoff64_reloc_type_br, /* R_RBR (0x1a) */
215 xcoff_reloc_type_ba, /* R_RBRC (0x1b) */
218 /* coffcode.h needs these to be defined. */
219 /* Internalcoff.h and coffcode.h modify themselves based on these flags. */
220 #define XCOFF64
221 #define RS6000COFF_C 1
223 #define SELECT_RELOC(internal, howto) \
225 internal.r_type = howto->type; \
226 internal.r_size = \
227 ((howto->complain_on_overflow == complain_overflow_signed \
228 ? 0x80 \
229 : 0) \
230 | (howto->bitsize - 1)); \
233 #define COFF_DEFAULT_SECTION_ALIGNMENT_POWER (3)
234 #define COFF_LONG_FILENAMES
235 #define NO_COFF_SYMBOLS
236 #define RTYPE2HOWTO(cache_ptr, dst) xcoff64_rtype2howto (cache_ptr, dst)
237 #define coff_mkobject _bfd_xcoff_mkobject
238 #define coff_bfd_copy_private_bfd_data _bfd_xcoff_copy_private_bfd_data
239 #define coff_bfd_is_local_label_name _bfd_xcoff_is_local_label_name
240 #define coff_bfd_reloc_type_lookup xcoff64_reloc_type_lookup
241 #define coff_bfd_reloc_name_lookup xcoff64_reloc_name_lookup
242 #ifdef AIX_CORE
243 extern const bfd_target * rs6000coff_core_p
244 PARAMS ((bfd *abfd));
245 extern bfd_boolean rs6000coff_core_file_matches_executable_p
246 PARAMS ((bfd *cbfd, bfd *ebfd));
247 extern char *rs6000coff_core_file_failing_command
248 PARAMS ((bfd *abfd));
249 extern int rs6000coff_core_file_failing_signal
250 PARAMS ((bfd *abfd));
251 #define CORE_FILE_P rs6000coff_core_p
252 #define coff_core_file_failing_command \
253 rs6000coff_core_file_failing_command
254 #define coff_core_file_failing_signal \
255 rs6000coff_core_file_failing_signal
256 #define coff_core_file_matches_executable_p \
257 rs6000coff_core_file_matches_executable_p
258 #else
259 #define CORE_FILE_P _bfd_dummy_target
260 #define coff_core_file_failing_command \
261 _bfd_nocore_core_file_failing_command
262 #define coff_core_file_failing_signal \
263 _bfd_nocore_core_file_failing_signal
264 #define coff_core_file_matches_executable_p \
265 _bfd_nocore_core_file_matches_executable_p
266 #endif
267 #define coff_SWAP_sym_in _bfd_xcoff64_swap_sym_in
268 #define coff_SWAP_sym_out _bfd_xcoff64_swap_sym_out
269 #define coff_SWAP_aux_in _bfd_xcoff64_swap_aux_in
270 #define coff_SWAP_aux_out _bfd_xcoff64_swap_aux_out
271 #define coff_swap_reloc_in xcoff64_swap_reloc_in
272 #define coff_swap_reloc_out xcoff64_swap_reloc_out
273 #define NO_COFF_RELOCS
275 #ifndef bfd_pe_print_pdata
276 #define bfd_pe_print_pdata NULL
277 #endif
279 #include "coffcode.h"
281 /* For XCOFF64, the effective width of symndx changes depending on
282 whether we are the first entry. Sigh. */
283 static void
284 _bfd_xcoff64_swap_lineno_in (abfd, ext1, in1)
285 bfd *abfd;
286 PTR ext1;
287 PTR in1;
289 LINENO *ext = (LINENO *) ext1;
290 struct internal_lineno *in = (struct internal_lineno *) in1;
292 in->l_lnno = H_GET_32 (abfd, (ext->l_lnno));
293 if (in->l_lnno == 0)
294 in->l_addr.l_symndx = H_GET_32 (abfd, ext->l_addr.l_symndx);
295 else
296 in->l_addr.l_paddr = H_GET_64 (abfd, ext->l_addr.l_paddr);
299 static unsigned int
300 _bfd_xcoff64_swap_lineno_out (abfd, inp, outp)
301 bfd *abfd;
302 PTR inp;
303 PTR outp;
305 struct internal_lineno *in = (struct internal_lineno *) inp;
306 struct external_lineno *ext = (struct external_lineno *) outp;
308 H_PUT_32 (abfd, in->l_addr.l_symndx, ext->l_addr.l_symndx);
309 H_PUT_32 (abfd, in->l_lnno, (ext->l_lnno));
311 if (in->l_lnno == 0)
312 H_PUT_32 (abfd, in->l_addr.l_symndx, ext->l_addr.l_symndx);
313 else
314 H_PUT_64 (abfd, in->l_addr.l_paddr, ext->l_addr.l_paddr);
316 return bfd_coff_linesz (abfd);
319 static void
320 _bfd_xcoff64_swap_sym_in (abfd, ext1, in1)
321 bfd *abfd;
322 PTR ext1;
323 PTR in1;
325 struct external_syment *ext = (struct external_syment *) ext1;
326 struct internal_syment *in = (struct internal_syment *) in1;
328 in->_n._n_n._n_zeroes = 0;
329 in->_n._n_n._n_offset = H_GET_32 (abfd, ext->e_offset);
330 in->n_value = H_GET_64 (abfd, ext->e_value);
331 in->n_scnum = H_GET_16 (abfd, ext->e_scnum);
332 in->n_type = H_GET_16 (abfd, ext->e_type);
333 in->n_sclass = H_GET_8 (abfd, ext->e_sclass);
334 in->n_numaux = H_GET_8 (abfd, ext->e_numaux);
337 static unsigned int
338 _bfd_xcoff64_swap_sym_out (abfd, inp, extp)
339 bfd *abfd;
340 PTR inp;
341 PTR extp;
343 struct internal_syment *in = (struct internal_syment *) inp;
344 struct external_syment *ext = (struct external_syment *) extp;
346 H_PUT_32 (abfd, in->_n._n_n._n_offset, ext->e_offset);
347 H_PUT_64 (abfd, in->n_value, ext->e_value);
348 H_PUT_16 (abfd, in->n_scnum, ext->e_scnum);
349 H_PUT_16 (abfd, in->n_type, ext->e_type);
350 H_PUT_8 (abfd, in->n_sclass, ext->e_sclass);
351 H_PUT_8 (abfd, in->n_numaux, ext->e_numaux);
352 return bfd_coff_symesz (abfd);
355 static void
356 _bfd_xcoff64_swap_aux_in (abfd, ext1, type, class, indx, numaux, in1)
357 bfd *abfd;
358 PTR ext1;
359 int type;
360 int class;
361 int indx;
362 int numaux;
363 PTR in1;
365 union external_auxent *ext = (union external_auxent *) ext1;
366 union internal_auxent *in = (union internal_auxent *) in1;
368 switch (class)
370 case C_FILE:
371 if (ext->x_file.x_n.x_zeroes[0] == 0)
373 in->x_file.x_n.x_zeroes = 0;
374 in->x_file.x_n.x_offset = H_GET_32 (abfd, ext->x_file.x_n.x_offset);
376 else
378 memcpy (in->x_file.x_fname, ext->x_file.x_fname, FILNMLEN);
380 goto end;
382 /* RS/6000 "csect" auxents */
383 case C_EXT:
384 case C_HIDEXT:
385 if (indx + 1 == numaux)
387 bfd_signed_vma h = 0;
388 bfd_vma l = 0;
390 h = H_GET_S32 (abfd, ext->x_csect.x_scnlen_hi);
391 l = H_GET_32 (abfd, ext->x_csect.x_scnlen_lo);
393 in->x_csect.x_scnlen.l = h << 32 | (l & 0xffffffff);
395 in->x_csect.x_parmhash = H_GET_32 (abfd, ext->x_csect.x_parmhash);
396 in->x_csect.x_snhash = H_GET_16 (abfd, ext->x_csect.x_snhash);
397 /* We don't have to hack bitfields in x_smtyp because it's
398 defined by shifts-and-ands, which are equivalent on all
399 byte orders. */
400 in->x_csect.x_smtyp = H_GET_8 (abfd, ext->x_csect.x_smtyp);
401 in->x_csect.x_smclas = H_GET_8 (abfd, ext->x_csect.x_smclas);
402 goto end;
404 break;
406 case C_STAT:
407 case C_LEAFSTAT:
408 case C_HIDDEN:
409 if (type == T_NULL)
411 /* PE defines some extra fields; we zero them out for
412 safety. */
413 in->x_scn.x_checksum = 0;
414 in->x_scn.x_associated = 0;
415 in->x_scn.x_comdat = 0;
417 goto end;
419 break;
422 if (class == C_BLOCK || class == C_FCN || ISFCN (type) || ISTAG (class))
424 in->x_sym.x_fcnary.x_fcn.x_lnnoptr
425 = H_GET_64 (abfd, ext->x_sym.x_fcnary.x_fcn.x_lnnoptr);
426 in->x_sym.x_fcnary.x_fcn.x_endndx.l
427 = H_GET_32 (abfd, ext->x_sym.x_fcnary.x_fcn.x_endndx);
429 if (ISFCN (type))
431 in->x_sym.x_misc.x_fsize
432 = H_GET_32 (abfd, ext->x_sym.x_fcnary.x_fcn.x_fsize);
434 else
436 in->x_sym.x_misc.x_lnsz.x_lnno
437 = H_GET_32 (abfd, ext->x_sym.x_fcnary.x_lnsz.x_lnno);
438 in->x_sym.x_misc.x_lnsz.x_size
439 = H_GET_16 (abfd, ext->x_sym.x_fcnary.x_lnsz.x_size);
442 end: ;
445 static unsigned int
446 _bfd_xcoff64_swap_aux_out (abfd, inp, type, class, indx, numaux, extp)
447 bfd *abfd;
448 PTR inp;
449 int type;
450 int class;
451 int indx ATTRIBUTE_UNUSED;
452 int numaux ATTRIBUTE_UNUSED;
453 PTR extp;
455 union internal_auxent *in = (union internal_auxent *) inp;
456 union external_auxent *ext = (union external_auxent *) extp;
458 memset ((PTR) ext, 0, bfd_coff_auxesz (abfd));
459 switch (class)
461 case C_FILE:
462 if (in->x_file.x_n.x_zeroes == 0)
464 H_PUT_32 (abfd, 0, ext->x_file.x_n.x_zeroes);
465 H_PUT_32 (abfd, in->x_file.x_n.x_offset, ext->x_file.x_n.x_offset);
467 else
469 memcpy (ext->x_file.x_fname, in->x_file.x_fname, FILNMLEN);
471 H_PUT_8 (abfd, _AUX_FILE, ext->x_auxtype.x_auxtype);
472 goto end;
474 /* RS/6000 "csect" auxents */
475 case C_EXT:
476 case C_HIDEXT:
477 if (indx + 1 == numaux)
479 bfd_vma temp;
481 temp = in->x_csect.x_scnlen.l & 0xffffffff;
482 H_PUT_32 (abfd, temp, ext->x_csect.x_scnlen_lo);
483 temp = in->x_csect.x_scnlen.l >> 32;
484 H_PUT_32 (abfd, temp, ext->x_csect.x_scnlen_hi);
485 H_PUT_32 (abfd, in->x_csect.x_parmhash, ext->x_csect.x_parmhash);
486 H_PUT_16 (abfd, in->x_csect.x_snhash, ext->x_csect.x_snhash);
487 /* We don't have to hack bitfields in x_smtyp because it's
488 defined by shifts-and-ands, which are equivalent on all
489 byte orders. */
490 H_PUT_8 (abfd, in->x_csect.x_smtyp, ext->x_csect.x_smtyp);
491 H_PUT_8 (abfd, in->x_csect.x_smclas, ext->x_csect.x_smclas);
492 H_PUT_8 (abfd, _AUX_CSECT, ext->x_auxtype.x_auxtype);
493 goto end;
495 break;
497 case C_STAT:
498 case C_LEAFSTAT:
499 case C_HIDDEN:
500 if (type == T_NULL)
502 goto end;
504 break;
507 if (class == C_BLOCK || class == C_FCN || ISFCN (type) || ISTAG (class))
509 H_PUT_64 (abfd, in->x_sym.x_fcnary.x_fcn.x_lnnoptr,
510 ext->x_sym.x_fcnary.x_fcn.x_lnnoptr);
511 H_PUT_8 (abfd, _AUX_FCN,
512 ext->x_auxtype.x_auxtype);
513 H_PUT_32 (abfd, in->x_sym.x_fcnary.x_fcn.x_endndx.l,
514 ext->x_sym.x_fcnary.x_fcn.x_endndx);
516 if (ISFCN (type))
518 H_PUT_32 (abfd, in->x_sym.x_misc.x_fsize,
519 ext->x_sym.x_fcnary.x_fcn.x_fsize);
521 else
523 H_PUT_32 (abfd, in->x_sym.x_misc.x_lnsz.x_lnno,
524 ext->x_sym.x_fcnary.x_lnsz.x_lnno);
525 H_PUT_16 (abfd, in->x_sym.x_misc.x_lnsz.x_size,
526 ext->x_sym.x_fcnary.x_lnsz.x_size);
529 end:
531 return bfd_coff_auxesz (abfd);
534 static bfd_boolean
535 _bfd_xcoff64_put_symbol_name (abfd, strtab, sym, name)
536 bfd *abfd;
537 struct bfd_strtab_hash *strtab;
538 struct internal_syment *sym;
539 const char *name;
541 bfd_boolean hash;
542 bfd_size_type indx;
544 hash = TRUE;
546 if ((abfd->flags & BFD_TRADITIONAL_FORMAT) != 0)
547 hash = FALSE;
549 indx = _bfd_stringtab_add (strtab, name, hash, FALSE);
551 if (indx == (bfd_size_type) -1)
552 return FALSE;
554 sym->_n._n_n._n_zeroes = 0;
555 sym->_n._n_n._n_offset = STRING_SIZE_SIZE + indx;
557 return TRUE;
560 static bfd_boolean
561 _bfd_xcoff64_put_ldsymbol_name (abfd, ldinfo, ldsym, name)
562 bfd *abfd ATTRIBUTE_UNUSED;
563 struct xcoff_loader_info *ldinfo;
564 struct internal_ldsym *ldsym;
565 const char *name;
567 size_t len;
568 len = strlen (name);
570 if (ldinfo->string_size + len + 3 > ldinfo->string_alc)
572 bfd_size_type newalc;
573 char *newstrings;
575 newalc = ldinfo->string_alc * 2;
576 if (newalc == 0)
577 newalc = 32;
578 while (ldinfo->string_size + len + 3 > newalc)
579 newalc *= 2;
581 newstrings = bfd_realloc (ldinfo->strings, newalc);
582 if (newstrings == NULL)
584 ldinfo->failed = TRUE;
585 return FALSE;
587 ldinfo->string_alc = newalc;
588 ldinfo->strings = newstrings;
591 bfd_put_16 (ldinfo->output_bfd, (bfd_vma) (len + 1),
592 ldinfo->strings + ldinfo->string_size);
593 strcpy (ldinfo->strings + ldinfo->string_size + 2, name);
594 ldsym->_l._l_l._l_zeroes = 0;
595 ldsym->_l._l_l._l_offset = ldinfo->string_size + 2;
596 ldinfo->string_size += len + 3;
598 return TRUE;
601 /* Routines to swap information in the XCOFF .loader section. If we
602 ever need to write an XCOFF loader, this stuff will need to be
603 moved to another file shared by the linker (which XCOFF calls the
604 ``binder'') and the loader. */
606 /* Swap in the ldhdr structure. */
608 static void
609 xcoff64_swap_ldhdr_in (abfd, s, dst)
610 bfd *abfd;
611 const PTR s;
612 struct internal_ldhdr *dst;
614 const struct external_ldhdr *src = (const struct external_ldhdr *) s;
616 dst->l_version = bfd_get_32 (abfd, src->l_version);
617 dst->l_nsyms = bfd_get_32 (abfd, src->l_nsyms);
618 dst->l_nreloc = bfd_get_32 (abfd, src->l_nreloc);
619 dst->l_istlen = bfd_get_32 (abfd, src->l_istlen);
620 dst->l_nimpid = bfd_get_32 (abfd, src->l_nimpid);
621 dst->l_stlen = bfd_get_32 (abfd, src->l_stlen);
622 dst->l_impoff = bfd_get_64 (abfd, src->l_impoff);
623 dst->l_stoff = bfd_get_64 (abfd, src->l_stoff);
624 dst->l_symoff = bfd_get_64 (abfd, src->l_symoff);
625 dst->l_rldoff = bfd_get_64 (abfd, src->l_rldoff);
628 /* Swap out the ldhdr structure. */
630 static void
631 xcoff64_swap_ldhdr_out (abfd, src, d)
632 bfd *abfd;
633 const struct internal_ldhdr *src;
634 PTR d;
636 struct external_ldhdr *dst = (struct external_ldhdr *) d;
638 bfd_put_32 (abfd, (bfd_vma) src->l_version, dst->l_version);
639 bfd_put_32 (abfd, src->l_nsyms, dst->l_nsyms);
640 bfd_put_32 (abfd, src->l_nreloc, dst->l_nreloc);
641 bfd_put_32 (abfd, src->l_istlen, dst->l_istlen);
642 bfd_put_32 (abfd, src->l_nimpid, dst->l_nimpid);
643 bfd_put_32 (abfd, src->l_stlen, dst->l_stlen);
644 bfd_put_64 (abfd, src->l_impoff, dst->l_impoff);
645 bfd_put_64 (abfd, src->l_stoff, dst->l_stoff);
646 bfd_put_64 (abfd, src->l_symoff, dst->l_symoff);
647 bfd_put_64 (abfd, src->l_rldoff, dst->l_rldoff);
650 /* Swap in the ldsym structure. */
652 static void
653 xcoff64_swap_ldsym_in (abfd, s, dst)
654 bfd *abfd;
655 const PTR s;
656 struct internal_ldsym *dst;
658 const struct external_ldsym *src = (const struct external_ldsym *) s;
659 /* XCOFF64 does not use l_zeroes like XCOFF32
660 Set the internal l_zeroes to 0 so the common 32/64 code uses l_value
661 as an offset into the loader symbol table. */
662 dst->_l._l_l._l_zeroes = 0;
663 dst->_l._l_l._l_offset = bfd_get_32 (abfd, src->l_offset);
664 dst->l_value = bfd_get_64 (abfd, src->l_value);
665 dst->l_scnum = bfd_get_16 (abfd, src->l_scnum);
666 dst->l_smtype = bfd_get_8 (abfd, src->l_smtype);
667 dst->l_smclas = bfd_get_8 (abfd, src->l_smclas);
668 dst->l_ifile = bfd_get_32 (abfd, src->l_ifile);
669 dst->l_parm = bfd_get_32 (abfd, src->l_parm);
672 /* Swap out the ldsym structure. */
674 static void
675 xcoff64_swap_ldsym_out (abfd, src, d)
676 bfd *abfd;
677 const struct internal_ldsym *src;
678 PTR d;
680 struct external_ldsym *dst = (struct external_ldsym *) d;
682 bfd_put_64 (abfd, src->l_value, dst->l_value);
683 bfd_put_32 (abfd, (bfd_vma) src->_l._l_l._l_offset, dst->l_offset);
684 bfd_put_16 (abfd, (bfd_vma) src->l_scnum, dst->l_scnum);
685 bfd_put_8 (abfd, src->l_smtype, dst->l_smtype);
686 bfd_put_8 (abfd, src->l_smclas, dst->l_smclas);
687 bfd_put_32 (abfd, src->l_ifile, dst->l_ifile);
688 bfd_put_32 (abfd, src->l_parm, dst->l_parm);
691 static void
692 xcoff64_swap_reloc_in (abfd, s, d)
693 bfd *abfd;
694 PTR s;
695 PTR d;
697 struct external_reloc *src = (struct external_reloc *) s;
698 struct internal_reloc *dst = (struct internal_reloc *) d;
700 memset (dst, 0, sizeof (struct internal_reloc));
702 dst->r_vaddr = bfd_get_64 (abfd, src->r_vaddr);
703 dst->r_symndx = bfd_get_32 (abfd, src->r_symndx);
704 dst->r_size = bfd_get_8 (abfd, src->r_size);
705 dst->r_type = bfd_get_8 (abfd, src->r_type);
708 static unsigned int
709 xcoff64_swap_reloc_out (abfd, s, d)
710 bfd *abfd;
711 PTR s;
712 PTR d;
714 struct internal_reloc *src = (struct internal_reloc *) s;
715 struct external_reloc *dst = (struct external_reloc *) d;
717 bfd_put_64 (abfd, src->r_vaddr, dst->r_vaddr);
718 bfd_put_32 (abfd, src->r_symndx, dst->r_symndx);
719 bfd_put_8 (abfd, src->r_type, dst->r_type);
720 bfd_put_8 (abfd, src->r_size, dst->r_size);
722 return bfd_coff_relsz (abfd);
725 /* Swap in the ldrel structure. */
727 static void
728 xcoff64_swap_ldrel_in (abfd, s, dst)
729 bfd *abfd;
730 const PTR s;
731 struct internal_ldrel *dst;
733 const struct external_ldrel *src = (const struct external_ldrel *) s;
735 dst->l_vaddr = bfd_get_64 (abfd, src->l_vaddr);
736 dst->l_symndx = bfd_get_32 (abfd, src->l_symndx);
737 dst->l_rtype = bfd_get_16 (abfd, src->l_rtype);
738 dst->l_rsecnm = bfd_get_16 (abfd, src->l_rsecnm);
741 /* Swap out the ldrel structure. */
743 static void
744 xcoff64_swap_ldrel_out (abfd, src, d)
745 bfd *abfd;
746 const struct internal_ldrel *src;
747 PTR d;
749 struct external_ldrel *dst = (struct external_ldrel *) d;
751 bfd_put_64 (abfd, src->l_vaddr, dst->l_vaddr);
752 bfd_put_16 (abfd, (bfd_vma) src->l_rtype, dst->l_rtype);
753 bfd_put_16 (abfd, (bfd_vma) src->l_rsecnm, dst->l_rsecnm);
754 bfd_put_32 (abfd, src->l_symndx, dst->l_symndx);
757 static bfd_boolean
758 xcoff64_write_object_contents (abfd)
759 bfd *abfd;
761 asection *current;
762 bfd_boolean hasrelocs = FALSE;
763 bfd_boolean haslinno = FALSE;
764 file_ptr scn_base;
765 file_ptr reloc_base;
766 file_ptr lineno_base;
767 file_ptr sym_base;
768 unsigned long reloc_size = 0;
769 unsigned long lnno_size = 0;
770 asection *text_sec = ((void *) 0);
771 asection *data_sec = ((void *) 0);
772 asection *bss_sec = ((void *) 0);
773 struct internal_filehdr internal_f;
774 struct internal_aouthdr internal_a;
776 bfd_set_error (bfd_error_system_call);
778 if (! abfd->output_has_begun)
780 if (! bfd_coff_compute_section_file_positions (abfd))
781 return FALSE;
784 /* Work out the size of the reloc and linno areas. */
785 reloc_base = obj_relocbase (abfd);
787 for (current = abfd->sections; current != NULL; current = current->next)
788 reloc_size += current->reloc_count * bfd_coff_relsz (abfd);
790 lineno_base = reloc_base + reloc_size;
792 /* Make a pass through the symbol table to count line number entries and
793 put them into the correct asections. */
794 lnno_size = coff_count_linenumbers (abfd) * bfd_coff_linesz (abfd);
796 sym_base = lineno_base + lnno_size;
798 /* Indicate in each section->line_filepos its actual file address. */
799 for (current = abfd->sections; current != NULL; current = current->next)
801 if (current->lineno_count)
803 current->line_filepos = lineno_base;
804 current->moving_line_filepos = lineno_base;
805 lineno_base += current->lineno_count * bfd_coff_linesz (abfd);
807 else
809 current->line_filepos = 0;
812 if (current->reloc_count)
814 current->rel_filepos = reloc_base;
815 reloc_base += current->reloc_count * bfd_coff_relsz (abfd);
817 else
819 current->rel_filepos = 0;
823 if ((abfd->flags & EXEC_P) != 0)
825 scn_base = bfd_coff_filhsz (abfd) + bfd_coff_aoutsz (abfd);
826 internal_f.f_opthdr = bfd_coff_aoutsz (abfd);
828 else
830 scn_base = bfd_coff_filhsz (abfd);
831 internal_f.f_opthdr = 0;
834 internal_f.f_nscns = 0;
836 if (bfd_seek (abfd, scn_base, SEEK_SET) != 0)
837 return FALSE;
839 for (current = abfd->sections; current != NULL; current = current->next)
841 struct internal_scnhdr section;
842 struct external_scnhdr buff;
843 bfd_size_type amount;
845 internal_f.f_nscns++;
847 strncpy (section.s_name, current->name, SCNNMLEN);
849 section.s_vaddr = current->vma;
850 section.s_paddr = current->lma;
851 section.s_size = current->size;
853 /* If this section has no size or is unloadable then the scnptr
854 will be 0 too. */
855 if (current->size == 0
856 || (current->flags & (SEC_LOAD | SEC_HAS_CONTENTS)) == 0)
858 section.s_scnptr = 0;
860 else
862 section.s_scnptr = current->filepos;
865 section.s_relptr = current->rel_filepos;
866 section.s_lnnoptr = current->line_filepos;
867 section.s_nreloc = current->reloc_count;
869 section.s_nlnno = current->lineno_count;
870 if (current->reloc_count != 0)
871 hasrelocs = TRUE;
872 if (current->lineno_count != 0)
873 haslinno = TRUE;
875 section.s_flags = sec_to_styp_flags (current->name, current->flags);
877 if (!strcmp (current->name, _TEXT))
879 text_sec = current;
881 else if (!strcmp (current->name, _DATA))
883 data_sec = current;
885 else if (!strcmp (current->name, _BSS))
887 bss_sec = current;
890 amount = bfd_coff_scnhsz (abfd);
891 if (bfd_coff_swap_scnhdr_out (abfd, &section, &buff) == 0
892 || bfd_bwrite ((PTR) (&buff), amount, abfd) != amount)
893 return FALSE;
896 internal_f.f_timdat = 0;
898 internal_f.f_flags = 0;
900 if (!hasrelocs)
901 internal_f.f_flags |= F_RELFLG;
902 if (!haslinno)
903 internal_f.f_flags |= F_LNNO;
904 if (abfd->flags & EXEC_P)
905 internal_f.f_flags |= F_EXEC;
907 /* FIXME: this is wrong for PPC_PE! */
908 if (bfd_little_endian (abfd))
909 internal_f.f_flags |= F_AR32WR;
910 else
911 internal_f.f_flags |= F_AR32W;
913 if ((abfd->flags & DYNAMIC) != 0)
914 internal_f.f_flags |= F_SHROBJ;
915 if (bfd_get_section_by_name (abfd, _LOADER) != NULL)
916 internal_f.f_flags |= F_DYNLOAD;
918 memset (&internal_a, 0, sizeof internal_a);
920 internal_f.f_magic = bfd_xcoff_magic_number (abfd);
921 internal_a.magic = (abfd->flags & D_PAGED
922 ? RS6K_AOUTHDR_ZMAGIC
923 : (abfd->flags & WP_TEXT
924 ? RS6K_AOUTHDR_NMAGIC
925 : RS6K_AOUTHDR_OMAGIC));
927 /* FIXME: Does anybody ever set this to another value? */
928 internal_a.vstamp = 0;
930 /* Now should write relocs, strings, syms. */
931 obj_sym_filepos (abfd) = sym_base;
933 internal_f.f_symptr = 0;
934 internal_f.f_nsyms = 0;
936 /* If bfd_get_symcount (abfd) != 0, then we are not using the COFF
937 backend linker, and obj_raw_syment_count is not valid until after
938 coff_write_symbols is called. */
939 if (bfd_get_symcount (abfd) != 0)
941 int firstundef;
943 if (!coff_renumber_symbols (abfd, &firstundef))
944 return FALSE;
945 coff_mangle_symbols (abfd);
946 if (! coff_write_symbols (abfd))
947 return FALSE;
948 if (! coff_write_linenumbers (abfd))
949 return FALSE;
950 if (! coff_write_relocs (abfd, firstundef))
951 return FALSE;
953 internal_f.f_symptr = sym_base;
954 internal_f.f_nsyms = bfd_get_symcount (abfd);
956 else if (obj_raw_syment_count (abfd) != 0)
958 internal_f.f_symptr = sym_base;
960 /* AIX appears to require that F_RELFLG not be set if there are
961 local symbols but no relocations. */
962 internal_f.f_flags &=~ F_RELFLG;
964 else
966 internal_f.f_flags |= F_LSYMS;
969 if (text_sec)
971 internal_a.tsize = text_sec->size;
972 internal_a.text_start = internal_a.tsize ? text_sec->vma : 0;
975 if (data_sec)
977 internal_a.dsize = data_sec->size;
978 internal_a.data_start = internal_a.dsize ? data_sec->vma : 0;
981 if (bss_sec)
983 internal_a.bsize = bss_sec->size;
984 if (internal_a.bsize && bss_sec->vma < internal_a.data_start)
985 internal_a.data_start = bss_sec->vma;
988 internal_a.entry = bfd_get_start_address (abfd);
989 internal_f.f_nsyms = obj_raw_syment_count (abfd);
991 if (xcoff_data (abfd)->full_aouthdr)
993 bfd_vma toc;
994 asection *loader_sec;
996 internal_a.vstamp = 1;
998 internal_a.o_snentry = xcoff_data (abfd)->snentry;
999 if (internal_a.o_snentry == 0)
1000 internal_a.entry = (bfd_vma) -1;
1002 if (text_sec != NULL)
1004 internal_a.o_sntext = text_sec->target_index;
1005 internal_a.o_algntext = bfd_get_section_alignment (abfd, text_sec);
1007 else
1009 internal_a.o_sntext = 0;
1010 internal_a.o_algntext = 0;
1013 if (data_sec != NULL)
1015 internal_a.o_sndata = data_sec->target_index;
1016 internal_a.o_algndata = bfd_get_section_alignment (abfd, data_sec);
1018 else
1020 internal_a.o_sndata = 0;
1021 internal_a.o_algndata = 0;
1024 loader_sec = bfd_get_section_by_name (abfd, ".loader");
1025 if (loader_sec != NULL)
1026 internal_a.o_snloader = loader_sec->target_index;
1027 else
1028 internal_a.o_snloader = 0;
1029 if (bss_sec != NULL)
1030 internal_a.o_snbss = bss_sec->target_index;
1031 else
1032 internal_a.o_snbss = 0;
1034 toc = xcoff_data (abfd)->toc;
1035 internal_a.o_toc = toc;
1036 internal_a.o_sntoc = xcoff_data (abfd)->sntoc;
1038 internal_a.o_modtype = xcoff_data (abfd)->modtype;
1039 if (xcoff_data (abfd)->cputype != -1)
1040 internal_a.o_cputype = xcoff_data (abfd)->cputype;
1041 else
1043 switch (bfd_get_arch (abfd))
1045 case bfd_arch_rs6000:
1046 internal_a.o_cputype = 4;
1047 break;
1048 case bfd_arch_powerpc:
1049 if (bfd_get_mach (abfd) == bfd_mach_ppc)
1050 internal_a.o_cputype = 3;
1051 else
1052 internal_a.o_cputype = 1;
1053 break;
1054 default:
1055 abort ();
1058 internal_a.o_maxstack = xcoff_data (abfd)->maxstack;
1059 internal_a.o_maxdata = xcoff_data (abfd)->maxdata;
1062 if (bfd_seek (abfd, (file_ptr) 0, 0) != 0)
1063 return FALSE;
1066 char * buff;
1067 bfd_size_type amount = bfd_coff_filhsz (abfd);
1069 buff = bfd_malloc (amount);
1070 if (buff == NULL)
1071 return FALSE;
1073 bfd_coff_swap_filehdr_out (abfd, (PTR) &internal_f, (PTR) buff);
1074 amount = bfd_bwrite ((PTR) buff, amount, abfd);
1076 free (buff);
1078 if (amount != bfd_coff_filhsz (abfd))
1079 return FALSE;
1082 if (abfd->flags & EXEC_P)
1084 char * buff;
1085 bfd_size_type amount = bfd_coff_aoutsz (abfd);
1087 buff = bfd_malloc (amount);
1088 if (buff == NULL)
1089 return FALSE;
1091 bfd_coff_swap_aouthdr_out (abfd, (PTR) &internal_a, (PTR) buff);
1092 amount = bfd_bwrite ((PTR) buff, amount, abfd);
1094 free (buff);
1096 if (amount != bfd_coff_aoutsz (abfd))
1097 return FALSE;
1100 return TRUE;
1103 static bfd_boolean
1104 xcoff64_reloc_type_br (input_bfd, input_section, output_bfd, rel, sym, howto,
1105 val, addend, relocation, contents)
1106 bfd *input_bfd;
1107 asection *input_section;
1108 bfd *output_bfd ATTRIBUTE_UNUSED;
1109 struct internal_reloc *rel;
1110 struct internal_syment *sym ATTRIBUTE_UNUSED;
1111 struct reloc_howto_struct *howto;
1112 bfd_vma val;
1113 bfd_vma addend;
1114 bfd_vma *relocation;
1115 bfd_byte *contents;
1117 struct xcoff_link_hash_entry *h;
1119 if (0 > rel->r_symndx)
1120 return FALSE;
1122 h = obj_xcoff_sym_hashes (input_bfd)[rel->r_symndx];
1124 /* If we see an R_BR or R_RBR reloc which is jumping to global
1125 linkage code, and it is followed by an appropriate cror nop
1126 instruction, we replace the cror with ld r2,40(r1). This
1127 restores the TOC after the glink code. Contrariwise, if the
1128 call is followed by a ld r2,40(r1), but the call is not
1129 going to global linkage code, we can replace the load with a
1130 cror. */
1131 if (NULL != h
1132 && bfd_link_hash_defined == h->root.type
1133 && rel->r_vaddr - input_section->vma + 8 <= input_section->size)
1135 bfd_byte *pnext;
1136 unsigned long next;
1138 pnext = contents + (rel->r_vaddr - input_section->vma) + 4;
1139 next = bfd_get_32 (input_bfd, pnext);
1141 /* The _ptrgl function is magic. It is used by the AIX compiler to call
1142 a function through a pointer. */
1143 if (h->smclas == XMC_GL || strcmp (h->root.root.string, "._ptrgl") == 0)
1145 if (next == 0x4def7b82 /* cror 15,15,15 */
1146 || next == 0x4ffffb82 /* cror 31,31,31 */
1147 || next == 0x60000000) /* ori r0,r0,0 */
1148 bfd_put_32 (input_bfd, 0xe8410028, pnext); /* ld r2,40(r1) */
1150 else
1152 if (next == 0xe8410028) /* ld r2,40(r1) */
1153 bfd_put_32 (input_bfd, 0x60000000, pnext); /* ori r0,r0,0 */
1156 else if (NULL != h && bfd_link_hash_undefined == h->root.type)
1158 /* Normally, this relocation is against a defined symbol. In the
1159 case where this is a partial link and the output section offset
1160 is greater than 2^25, the linker will return an invalid error
1161 message that the relocation has been truncated. Yes it has been
1162 truncated but no it not important. For this case, disable the
1163 overflow checking. */
1164 howto->complain_on_overflow = complain_overflow_dont;
1167 howto->pc_relative = TRUE;
1168 howto->src_mask &= ~3;
1169 howto->dst_mask = howto->src_mask;
1171 /* A PC relative reloc includes the section address. */
1172 addend += input_section->vma;
1174 *relocation = val + addend;
1175 *relocation -= (input_section->output_section->vma
1176 + input_section->output_offset);
1177 return TRUE;
1180 /* This is the relocation function for the PowerPC64.
1181 See xcoff_ppc_relocation_section for more information. */
1183 bfd_boolean
1184 xcoff64_ppc_relocate_section (output_bfd, info, input_bfd,
1185 input_section, contents, relocs, syms,
1186 sections)
1187 bfd *output_bfd;
1188 struct bfd_link_info *info;
1189 bfd *input_bfd;
1190 asection *input_section;
1191 bfd_byte *contents;
1192 struct internal_reloc *relocs;
1193 struct internal_syment *syms;
1194 asection **sections;
1196 struct internal_reloc *rel;
1197 struct internal_reloc *relend;
1199 rel = relocs;
1200 relend = rel + input_section->reloc_count;
1201 for (; rel < relend; rel++)
1203 long symndx;
1204 struct xcoff_link_hash_entry *h;
1205 struct internal_syment *sym;
1206 bfd_vma addend;
1207 bfd_vma val;
1208 struct reloc_howto_struct howto;
1209 bfd_vma relocation;
1210 bfd_vma value_to_relocate;
1211 bfd_vma address;
1212 bfd_byte *location;
1214 /* Relocation type R_REF is a special relocation type which is
1215 merely used to prevent garbage collection from occurring for
1216 the csect including the symbol which it references. */
1217 if (rel->r_type == R_REF)
1218 continue;
1220 /* howto */
1221 howto.type = rel->r_type;
1222 howto.rightshift = 0;
1223 howto.bitsize = (rel->r_size & 0x3f) + 1;
1224 howto.size = howto.bitsize > 16 ? (howto.bitsize > 32 ? 4 : 2) : 1;
1225 howto.pc_relative = FALSE;
1226 howto.bitpos = 0;
1227 howto.complain_on_overflow = (rel->r_size & 0x80
1228 ? complain_overflow_signed
1229 : complain_overflow_bitfield);
1230 howto.special_function = NULL;
1231 howto.name = "internal";
1232 howto.partial_inplace = TRUE;
1233 howto.src_mask = howto.dst_mask = N_ONES (howto.bitsize);
1234 howto.pcrel_offset = FALSE;
1236 /* symbol */
1237 val = 0;
1238 addend = 0;
1239 h = NULL;
1240 sym = NULL;
1241 symndx = rel->r_symndx;
1243 if (-1 != symndx)
1245 asection *sec;
1247 h = obj_xcoff_sym_hashes (input_bfd)[symndx];
1248 sym = syms + symndx;
1249 addend = - sym->n_value;
1251 if (NULL == h)
1253 sec = sections[symndx];
1254 /* Hack to make sure we use the right TOC anchor value
1255 if this reloc is against the TOC anchor. */
1256 if (sec->name[3] == '0'
1257 && strcmp (sec->name, ".tc0") == 0)
1258 val = xcoff_data (output_bfd)->toc;
1259 else
1260 val = (sec->output_section->vma
1261 + sec->output_offset
1262 + sym->n_value
1263 - sec->vma);
1265 else
1267 if (h->root.type == bfd_link_hash_defined
1268 || h->root.type == bfd_link_hash_defweak)
1270 sec = h->root.u.def.section;
1271 val = (h->root.u.def.value
1272 + sec->output_section->vma
1273 + sec->output_offset);
1275 else if (h->root.type == bfd_link_hash_common)
1277 sec = h->root.u.c.p->section;
1278 val = (sec->output_section->vma
1279 + sec->output_offset);
1281 else if ((0 == (h->flags & (XCOFF_DEF_DYNAMIC | XCOFF_IMPORT)))
1282 && ! info->relocatable)
1284 if (! ((*info->callbacks->undefined_symbol)
1285 (info, h->root.root.string, input_bfd, input_section,
1286 rel->r_vaddr - input_section->vma, TRUE)))
1287 return FALSE;
1289 /* Don't try to process the reloc. It can't help, and
1290 it may generate another error. */
1291 continue;
1296 if (rel->r_type >= XCOFF_MAX_CALCULATE_RELOCATION
1297 || !((*xcoff64_calculate_relocation[rel->r_type])
1298 (input_bfd, input_section, output_bfd, rel, sym, &howto, val,
1299 addend, &relocation, contents)))
1300 return FALSE;
1302 /* address */
1303 address = rel->r_vaddr - input_section->vma;
1304 location = contents + address;
1306 if (address > input_section->size)
1307 abort ();
1309 /* Get the value we are going to relocate. */
1310 if (1 == howto.size)
1311 value_to_relocate = bfd_get_16 (input_bfd, location);
1312 else if (2 == howto.size)
1313 value_to_relocate = bfd_get_32 (input_bfd, location);
1314 else
1315 value_to_relocate = bfd_get_64 (input_bfd, location);
1317 /* overflow.
1319 FIXME: We may drop bits during the addition
1320 which we don't check for. We must either check at every single
1321 operation, which would be tedious, or we must do the computations
1322 in a type larger than bfd_vma, which would be inefficient. */
1324 if ((unsigned int) howto.complain_on_overflow
1325 >= XCOFF_MAX_COMPLAIN_OVERFLOW)
1326 abort ();
1328 if (((*xcoff_complain_overflow[howto.complain_on_overflow])
1329 (input_bfd, value_to_relocate, relocation, &howto)))
1331 const char *name;
1332 char buf[SYMNMLEN + 1];
1333 char reloc_type_name[10];
1335 if (symndx == -1)
1337 name = "*ABS*";
1339 else if (h != NULL)
1341 name = NULL;
1343 else
1345 name = _bfd_coff_internal_syment_name (input_bfd, sym, buf);
1346 if (name == NULL)
1347 name = "UNKNOWN";
1349 sprintf (reloc_type_name, "0x%02x", rel->r_type);
1351 if (! ((*info->callbacks->reloc_overflow)
1352 (info, (h ? &h->root : NULL), name, reloc_type_name,
1353 (bfd_vma) 0, input_bfd, input_section,
1354 rel->r_vaddr - input_section->vma)))
1355 return FALSE;
1358 /* Add RELOCATION to the right bits of VALUE_TO_RELOCATE. */
1359 value_to_relocate = ((value_to_relocate & ~howto.dst_mask)
1360 | (((value_to_relocate & howto.src_mask)
1361 + relocation) & howto.dst_mask));
1363 /* Put the value back in the object file. */
1364 if (1 == howto.size)
1365 bfd_put_16 (input_bfd, value_to_relocate, location);
1366 else if (2 == howto.size)
1367 bfd_put_32 (input_bfd, value_to_relocate, location);
1368 else
1369 bfd_put_64 (input_bfd, value_to_relocate, location);
1372 return TRUE;
1376 /* The XCOFF reloc table. Actually, XCOFF relocations specify the
1377 bitsize and whether they are signed or not, along with a
1378 conventional type. This table is for the types, which are used for
1379 different algorithms for putting in the reloc. Many of these
1380 relocs need special_function entries, which I have not written. */
1382 reloc_howto_type xcoff64_howto_table[] =
1384 /* Standard 64 bit relocation. */
1385 HOWTO (R_POS, /* type */
1386 0, /* rightshift */
1387 4, /* size (0 = byte, 1 = short, 2 = long) */
1388 64, /* bitsize */
1389 FALSE, /* pc_relative */
1390 0, /* bitpos */
1391 complain_overflow_bitfield, /* complain_on_overflow */
1392 0, /* special_function */
1393 "R_POS_64", /* name */
1394 TRUE, /* partial_inplace */
1395 MINUS_ONE, /* src_mask */
1396 MINUS_ONE, /* dst_mask */
1397 FALSE), /* pcrel_offset */
1399 /* 64 bit relocation, but store negative value. */
1400 HOWTO (R_NEG, /* type */
1401 0, /* rightshift */
1402 -4, /* size (0 = byte, 1 = short, 2 = long) */
1403 64, /* bitsize */
1404 FALSE, /* pc_relative */
1405 0, /* bitpos */
1406 complain_overflow_bitfield, /* complain_on_overflow */
1407 0, /* special_function */
1408 "R_NEG", /* name */
1409 TRUE, /* partial_inplace */
1410 MINUS_ONE, /* src_mask */
1411 MINUS_ONE, /* dst_mask */
1412 FALSE), /* pcrel_offset */
1414 /* 32 bit PC relative relocation. */
1415 HOWTO (R_REL, /* type */
1416 0, /* rightshift */
1417 2, /* size (0 = byte, 1 = short, 2 = long) */
1418 32, /* bitsize */
1419 TRUE, /* pc_relative */
1420 0, /* bitpos */
1421 complain_overflow_signed, /* complain_on_overflow */
1422 0, /* special_function */
1423 "R_REL", /* name */
1424 TRUE, /* partial_inplace */
1425 0xffffffff, /* src_mask */
1426 0xffffffff, /* dst_mask */
1427 FALSE), /* pcrel_offset */
1429 /* 16 bit TOC relative relocation. */
1430 HOWTO (R_TOC, /* type */
1431 0, /* rightshift */
1432 1, /* size (0 = byte, 1 = short, 2 = long) */
1433 16, /* bitsize */
1434 FALSE, /* pc_relative */
1435 0, /* bitpos */
1436 complain_overflow_bitfield, /* complain_on_overflow */
1437 0, /* special_function */
1438 "R_TOC", /* name */
1439 TRUE, /* partial_inplace */
1440 0xffff, /* src_mask */
1441 0xffff, /* dst_mask */
1442 FALSE), /* pcrel_offset */
1444 /* I don't really know what this is. */
1445 HOWTO (R_RTB, /* type */
1446 1, /* rightshift */
1447 2, /* size (0 = byte, 1 = short, 2 = long) */
1448 32, /* bitsize */
1449 FALSE, /* pc_relative */
1450 0, /* bitpos */
1451 complain_overflow_bitfield, /* complain_on_overflow */
1452 0, /* special_function */
1453 "R_RTB", /* name */
1454 TRUE, /* partial_inplace */
1455 0xffffffff, /* src_mask */
1456 0xffffffff, /* dst_mask */
1457 FALSE), /* pcrel_offset */
1459 /* External TOC relative symbol. */
1460 HOWTO (R_GL, /* type */
1461 0, /* rightshift */
1462 1, /* size (0 = byte, 1 = short, 2 = long) */
1463 16, /* bitsize */
1464 FALSE, /* pc_relative */
1465 0, /* bitpos */
1466 complain_overflow_bitfield, /* complain_on_overflow */
1467 0, /* special_function */
1468 "R_GL", /* name */
1469 TRUE, /* partial_inplace */
1470 0xffff, /* src_mask */
1471 0xffff, /* dst_mask */
1472 FALSE), /* pcrel_offset */
1474 /* Local TOC relative symbol. */
1475 HOWTO (R_TCL, /* type */
1476 0, /* rightshift */
1477 1, /* size (0 = byte, 1 = short, 2 = long) */
1478 16, /* bitsize */
1479 FALSE, /* pc_relative */
1480 0, /* bitpos */
1481 complain_overflow_bitfield, /* complain_on_overflow */
1482 0, /* special_function */
1483 "R_TCL", /* name */
1484 TRUE, /* partial_inplace */
1485 0xffff, /* src_mask */
1486 0xffff, /* dst_mask */
1487 FALSE), /* pcrel_offset */
1489 EMPTY_HOWTO (7),
1491 /* Non modifiable absolute branch. */
1492 HOWTO (R_BA, /* type */
1493 0, /* rightshift */
1494 2, /* size (0 = byte, 1 = short, 2 = long) */
1495 26, /* bitsize */
1496 FALSE, /* pc_relative */
1497 0, /* bitpos */
1498 complain_overflow_bitfield, /* complain_on_overflow */
1499 0, /* special_function */
1500 "R_BA_26", /* name */
1501 TRUE, /* partial_inplace */
1502 0x03fffffc, /* src_mask */
1503 0x03fffffc, /* dst_mask */
1504 FALSE), /* pcrel_offset */
1506 EMPTY_HOWTO (9),
1508 /* Non modifiable relative branch. */
1509 HOWTO (R_BR, /* type */
1510 0, /* rightshift */
1511 2, /* size (0 = byte, 1 = short, 2 = long) */
1512 26, /* bitsize */
1513 TRUE, /* pc_relative */
1514 0, /* bitpos */
1515 complain_overflow_signed, /* complain_on_overflow */
1516 0, /* special_function */
1517 "R_BR", /* name */
1518 TRUE, /* partial_inplace */
1519 0x03fffffc, /* src_mask */
1520 0x03fffffc, /* dst_mask */
1521 FALSE), /* pcrel_offset */
1523 EMPTY_HOWTO (0xb),
1525 /* Indirect load. */
1526 HOWTO (R_RL, /* type */
1527 0, /* rightshift */
1528 1, /* size (0 = byte, 1 = short, 2 = long) */
1529 16, /* bitsize */
1530 FALSE, /* pc_relative */
1531 0, /* bitpos */
1532 complain_overflow_bitfield, /* complain_on_overflow */
1533 0, /* special_function */
1534 "R_RL", /* name */
1535 TRUE, /* partial_inplace */
1536 0xffff, /* src_mask */
1537 0xffff, /* dst_mask */
1538 FALSE), /* pcrel_offset */
1540 /* Load address. */
1541 HOWTO (R_RLA, /* type */
1542 0, /* rightshift */
1543 1, /* size (0 = byte, 1 = short, 2 = long) */
1544 16, /* bitsize */
1545 FALSE, /* pc_relative */
1546 0, /* bitpos */
1547 complain_overflow_bitfield, /* complain_on_overflow */
1548 0, /* special_function */
1549 "R_RLA", /* name */
1550 TRUE, /* partial_inplace */
1551 0xffff, /* src_mask */
1552 0xffff, /* dst_mask */
1553 FALSE), /* pcrel_offset */
1555 EMPTY_HOWTO (0xe),
1557 /* Non-relocating reference. */
1558 HOWTO (R_REF, /* type */
1559 0, /* rightshift */
1560 2, /* size (0 = byte, 1 = short, 2 = long) */
1561 32, /* bitsize */
1562 FALSE, /* pc_relative */
1563 0, /* bitpos */
1564 complain_overflow_dont, /* complain_on_overflow */
1565 0, /* special_function */
1566 "R_REF", /* name */
1567 FALSE, /* partial_inplace */
1568 0, /* src_mask */
1569 0, /* dst_mask */
1570 FALSE), /* pcrel_offset */
1572 EMPTY_HOWTO (0x10),
1573 EMPTY_HOWTO (0x11),
1575 /* TOC relative indirect load. */
1576 HOWTO (R_TRL, /* type */
1577 0, /* rightshift */
1578 1, /* size (0 = byte, 1 = short, 2 = long) */
1579 16, /* bitsize */
1580 FALSE, /* pc_relative */
1581 0, /* bitpos */
1582 complain_overflow_bitfield, /* complain_on_overflow */
1583 0, /* special_function */
1584 "R_TRL", /* name */
1585 TRUE, /* partial_inplace */
1586 0xffff, /* src_mask */
1587 0xffff, /* dst_mask */
1588 FALSE), /* pcrel_offset */
1590 /* TOC relative load address. */
1591 HOWTO (R_TRLA, /* type */
1592 0, /* rightshift */
1593 1, /* size (0 = byte, 1 = short, 2 = long) */
1594 16, /* bitsize */
1595 FALSE, /* pc_relative */
1596 0, /* bitpos */
1597 complain_overflow_bitfield, /* complain_on_overflow */
1598 0, /* special_function */
1599 "R_TRLA", /* name */
1600 TRUE, /* partial_inplace */
1601 0xffff, /* src_mask */
1602 0xffff, /* dst_mask */
1603 FALSE), /* pcrel_offset */
1605 /* Modifiable relative branch. */
1606 HOWTO (R_RRTBI, /* type */
1607 1, /* rightshift */
1608 2, /* size (0 = byte, 1 = short, 2 = long) */
1609 32, /* bitsize */
1610 FALSE, /* pc_relative */
1611 0, /* bitpos */
1612 complain_overflow_bitfield, /* complain_on_overflow */
1613 0, /* special_function */
1614 "R_RRTBI", /* name */
1615 TRUE, /* partial_inplace */
1616 0xffffffff, /* src_mask */
1617 0xffffffff, /* dst_mask */
1618 FALSE), /* pcrel_offset */
1620 /* Modifiable absolute branch. */
1621 HOWTO (R_RRTBA, /* type */
1622 1, /* rightshift */
1623 2, /* size (0 = byte, 1 = short, 2 = long) */
1624 32, /* bitsize */
1625 FALSE, /* pc_relative */
1626 0, /* bitpos */
1627 complain_overflow_bitfield, /* complain_on_overflow */
1628 0, /* special_function */
1629 "R_RRTBA", /* name */
1630 TRUE, /* partial_inplace */
1631 0xffffffff, /* src_mask */
1632 0xffffffff, /* dst_mask */
1633 FALSE), /* pcrel_offset */
1635 /* Modifiable call absolute indirect. */
1636 HOWTO (R_CAI, /* type */
1637 0, /* rightshift */
1638 1, /* size (0 = byte, 1 = short, 2 = long) */
1639 16, /* bitsize */
1640 FALSE, /* pc_relative */
1641 0, /* bitpos */
1642 complain_overflow_bitfield, /* complain_on_overflow */
1643 0, /* special_function */
1644 "R_CAI", /* name */
1645 TRUE, /* partial_inplace */
1646 0xffff, /* src_mask */
1647 0xffff, /* dst_mask */
1648 FALSE), /* pcrel_offset */
1650 /* Modifiable call relative. */
1651 HOWTO (R_CREL, /* type */
1652 0, /* rightshift */
1653 1, /* size (0 = byte, 1 = short, 2 = long) */
1654 16, /* bitsize */
1655 FALSE, /* pc_relative */
1656 0, /* bitpos */
1657 complain_overflow_bitfield, /* complain_on_overflow */
1658 0, /* special_function */
1659 "R_CREL", /* name */
1660 TRUE, /* partial_inplace */
1661 0xffff, /* src_mask */
1662 0xffff, /* dst_mask */
1663 FALSE), /* pcrel_offset */
1665 /* Modifiable branch absolute. */
1666 HOWTO (R_RBA, /* type */
1667 0, /* rightshift */
1668 2, /* size (0 = byte, 1 = short, 2 = long) */
1669 26, /* bitsize */
1670 FALSE, /* pc_relative */
1671 0, /* bitpos */
1672 complain_overflow_bitfield, /* complain_on_overflow */
1673 0, /* special_function */
1674 "R_RBA", /* name */
1675 TRUE, /* partial_inplace */
1676 0x03fffffc, /* src_mask */
1677 0x03fffffc, /* dst_mask */
1678 FALSE), /* pcrel_offset */
1680 /* Modifiable branch absolute. */
1681 HOWTO (R_RBAC, /* type */
1682 0, /* rightshift */
1683 2, /* size (0 = byte, 1 = short, 2 = long) */
1684 32, /* bitsize */
1685 FALSE, /* pc_relative */
1686 0, /* bitpos */
1687 complain_overflow_bitfield, /* complain_on_overflow */
1688 0, /* special_function */
1689 "R_RBAC", /* name */
1690 TRUE, /* partial_inplace */
1691 0xffffffff, /* src_mask */
1692 0xffffffff, /* dst_mask */
1693 FALSE), /* pcrel_offset */
1695 /* Modifiable branch relative. */
1696 HOWTO (R_RBR, /* type */
1697 0, /* rightshift */
1698 2, /* size (0 = byte, 1 = short, 2 = long) */
1699 26, /* bitsize */
1700 FALSE, /* pc_relative */
1701 0, /* bitpos */
1702 complain_overflow_signed, /* complain_on_overflow */
1703 0, /* special_function */
1704 "R_RBR_26", /* name */
1705 TRUE, /* partial_inplace */
1706 0x03fffffc, /* src_mask */
1707 0x03fffffc, /* dst_mask */
1708 FALSE), /* pcrel_offset */
1710 /* Modifiable branch absolute. */
1711 HOWTO (R_RBRC, /* type */
1712 0, /* rightshift */
1713 1, /* size (0 = byte, 1 = short, 2 = long) */
1714 16, /* bitsize */
1715 FALSE, /* pc_relative */
1716 0, /* bitpos */
1717 complain_overflow_bitfield, /* complain_on_overflow */
1718 0, /* special_function */
1719 "R_RBRC", /* name */
1720 TRUE, /* partial_inplace */
1721 0xffff, /* src_mask */
1722 0xffff, /* dst_mask */
1723 FALSE), /* pcrel_offset */
1725 HOWTO (R_POS, /* type */
1726 0, /* rightshift */
1727 2, /* size (0 = byte, 1 = short, 2 = long) */
1728 32, /* bitsize */
1729 FALSE, /* pc_relative */
1730 0, /* bitpos */
1731 complain_overflow_bitfield, /* complain_on_overflow */
1732 0, /* special_function */
1733 "R_POS_32", /* name */
1734 TRUE, /* partial_inplace */
1735 0xffffffff, /* src_mask */
1736 0xffffffff, /* dst_mask */
1737 FALSE), /* pcrel_offset */
1739 /* 16 bit Non modifiable absolute branch. */
1740 HOWTO (R_BA, /* type */
1741 0, /* rightshift */
1742 1, /* size (0 = byte, 1 = short, 2 = long) */
1743 16, /* bitsize */
1744 FALSE, /* pc_relative */
1745 0, /* bitpos */
1746 complain_overflow_bitfield, /* complain_on_overflow */
1747 0, /* special_function */
1748 "R_BA_16", /* name */
1749 TRUE, /* partial_inplace */
1750 0xfffc, /* src_mask */
1751 0xfffc, /* dst_mask */
1752 FALSE), /* pcrel_offset */
1754 /* Modifiable branch relative. */
1755 HOWTO (R_RBR, /* type */
1756 0, /* rightshift */
1757 1, /* size (0 = byte, 1 = short, 2 = long) */
1758 16, /* bitsize */
1759 FALSE, /* pc_relative */
1760 0, /* bitpos */
1761 complain_overflow_signed, /* complain_on_overflow */
1762 0, /* special_function */
1763 "R_RBR_16", /* name */
1764 TRUE, /* partial_inplace */
1765 0xffff, /* src_mask */
1766 0xffff, /* dst_mask */
1767 FALSE), /* pcrel_offset */
1769 /* Modifiable branch absolute. */
1770 HOWTO (R_RBA, /* type */
1771 0, /* rightshift */
1772 1, /* size (0 = byte, 1 = short, 2 = long) */
1773 16, /* bitsize */
1774 FALSE, /* pc_relative */
1775 0, /* bitpos */
1776 complain_overflow_bitfield, /* complain_on_overflow */
1777 0, /* special_function */
1778 "R_RBA_16", /* name */
1779 TRUE, /* partial_inplace */
1780 0xffff, /* src_mask */
1781 0xffff, /* dst_mask */
1782 FALSE), /* pcrel_offset */
1786 void
1787 xcoff64_rtype2howto (relent, internal)
1788 arelent *relent;
1789 struct internal_reloc *internal;
1791 if (internal->r_type > R_RBRC)
1792 abort ();
1794 /* Default howto layout works most of the time */
1795 relent->howto = &xcoff64_howto_table[internal->r_type];
1797 /* Special case some 16 bit reloc */
1798 if (15 == (internal->r_size & 0x3f))
1800 if (R_BA == internal->r_type)
1801 relent->howto = &xcoff64_howto_table[0x1d];
1802 else if (R_RBR == internal->r_type)
1803 relent->howto = &xcoff64_howto_table[0x1e];
1804 else if (R_RBA == internal->r_type)
1805 relent->howto = &xcoff64_howto_table[0x1f];
1807 /* Special case 32 bit */
1808 else if (31 == (internal->r_size & 0x3f))
1810 if (R_POS == internal->r_type)
1811 relent->howto = &xcoff64_howto_table[0x1c];
1814 /* The r_size field of an XCOFF reloc encodes the bitsize of the
1815 relocation, as well as indicating whether it is signed or not.
1816 Doublecheck that the relocation information gathered from the
1817 type matches this information. The bitsize is not significant
1818 for R_REF relocs. */
1819 if (relent->howto->dst_mask != 0
1820 && (relent->howto->bitsize
1821 != ((unsigned int) internal->r_size & 0x3f) + 1))
1822 abort ();
1825 reloc_howto_type *
1826 xcoff64_reloc_type_lookup (abfd, code)
1827 bfd *abfd ATTRIBUTE_UNUSED;
1828 bfd_reloc_code_real_type code;
1830 switch (code)
1832 case BFD_RELOC_PPC_B26:
1833 return &xcoff64_howto_table[0xa];
1834 case BFD_RELOC_PPC_BA16:
1835 return &xcoff64_howto_table[0x1d];
1836 case BFD_RELOC_PPC_BA26:
1837 return &xcoff64_howto_table[8];
1838 case BFD_RELOC_PPC_TOC16:
1839 return &xcoff64_howto_table[3];
1840 case BFD_RELOC_32:
1841 case BFD_RELOC_CTOR:
1842 return &xcoff64_howto_table[0x1c];
1843 case BFD_RELOC_64:
1844 return &xcoff64_howto_table[0];
1845 default:
1846 return NULL;
1850 static reloc_howto_type *
1851 xcoff64_reloc_name_lookup (bfd *abfd ATTRIBUTE_UNUSED,
1852 const char *r_name)
1854 unsigned int i;
1856 for (i = 0;
1857 i < sizeof (xcoff64_howto_table) / sizeof (xcoff64_howto_table[0]);
1858 i++)
1859 if (xcoff64_howto_table[i].name != NULL
1860 && strcasecmp (xcoff64_howto_table[i].name, r_name) == 0)
1861 return &xcoff64_howto_table[i];
1863 return NULL;
1866 /* Read in the armap of an XCOFF archive. */
1868 static bfd_boolean
1869 xcoff64_slurp_armap (abfd)
1870 bfd *abfd;
1872 file_ptr off;
1873 size_t namlen;
1874 bfd_size_type sz, amt;
1875 bfd_byte *contents, *cend;
1876 bfd_vma c, i;
1877 carsym *arsym;
1878 bfd_byte *p;
1879 file_ptr pos;
1881 /* This is for the new format. */
1882 struct xcoff_ar_hdr_big hdr;
1884 if (xcoff_ardata (abfd) == NULL)
1886 bfd_has_map (abfd) = FALSE;
1887 return TRUE;
1890 off = bfd_scan_vma (xcoff_ardata_big (abfd)->symoff64,
1891 (const char **) NULL, 10);
1892 if (off == 0)
1894 bfd_has_map (abfd) = FALSE;
1895 return TRUE;
1898 if (bfd_seek (abfd, off, SEEK_SET) != 0)
1899 return FALSE;
1901 /* The symbol table starts with a normal archive header. */
1902 if (bfd_bread ((PTR) &hdr, (bfd_size_type) SIZEOF_AR_HDR_BIG, abfd)
1903 != SIZEOF_AR_HDR_BIG)
1904 return FALSE;
1906 /* Skip the name (normally empty). */
1907 namlen = strtol (hdr.namlen, (char **) NULL, 10);
1908 pos = ((namlen + 1) & ~(size_t) 1) + SXCOFFARFMAG;
1909 if (bfd_seek (abfd, pos, SEEK_CUR) != 0)
1910 return FALSE;
1912 sz = bfd_scan_vma (hdr.size, (const char **) NULL, 10);
1914 /* Read in the entire symbol table. */
1915 contents = (bfd_byte *) bfd_alloc (abfd, sz);
1916 if (contents == NULL)
1917 return FALSE;
1918 if (bfd_bread ((PTR) contents, sz, abfd) != sz)
1919 return FALSE;
1921 /* The symbol table starts with an eight byte count. */
1922 c = H_GET_64 (abfd, contents);
1924 if (c * 8 >= sz)
1926 bfd_set_error (bfd_error_bad_value);
1927 return FALSE;
1929 amt = c;
1930 amt *= sizeof (carsym);
1931 bfd_ardata (abfd)->symdefs = (carsym *) bfd_alloc (abfd, amt);
1932 if (bfd_ardata (abfd)->symdefs == NULL)
1933 return FALSE;
1935 /* After the count comes a list of eight byte file offsets. */
1936 for (i = 0, arsym = bfd_ardata (abfd)->symdefs, p = contents + 8;
1937 i < c;
1938 ++i, ++arsym, p += 8)
1939 arsym->file_offset = H_GET_64 (abfd, p);
1941 /* After the file offsets come null terminated symbol names. */
1942 cend = contents + sz;
1943 for (i = 0, arsym = bfd_ardata (abfd)->symdefs;
1944 i < c;
1945 ++i, ++arsym, p += strlen ((char *) p) + 1)
1947 if (p >= cend)
1949 bfd_set_error (bfd_error_bad_value);
1950 return FALSE;
1952 arsym->name = (char *) p;
1955 bfd_ardata (abfd)->symdef_count = c;
1956 bfd_has_map (abfd) = TRUE;
1958 return TRUE;
1962 /* See if this is an NEW XCOFF archive. */
1964 static const bfd_target *
1965 xcoff64_archive_p (abfd)
1966 bfd *abfd;
1968 struct artdata *tdata_hold;
1969 char magic[SXCOFFARMAG];
1970 /* This is the new format. */
1971 struct xcoff_ar_file_hdr_big hdr;
1972 bfd_size_type amt = SXCOFFARMAG;
1974 if (bfd_bread ((PTR) magic, amt, abfd) != amt)
1976 if (bfd_get_error () != bfd_error_system_call)
1977 bfd_set_error (bfd_error_wrong_format);
1978 return NULL;
1981 if (strncmp (magic, XCOFFARMAGBIG, SXCOFFARMAG) != 0)
1983 bfd_set_error (bfd_error_wrong_format);
1984 return NULL;
1987 /* Copy over the magic string. */
1988 memcpy (hdr.magic, magic, SXCOFFARMAG);
1990 /* Now read the rest of the file header. */
1991 amt = SIZEOF_AR_FILE_HDR_BIG - SXCOFFARMAG;
1992 if (bfd_bread ((PTR) &hdr.memoff, amt, abfd) != amt)
1994 if (bfd_get_error () != bfd_error_system_call)
1995 bfd_set_error (bfd_error_wrong_format);
1996 return NULL;
1999 tdata_hold = bfd_ardata (abfd);
2001 amt = sizeof (struct artdata);
2002 bfd_ardata (abfd) = (struct artdata *) bfd_zalloc (abfd, amt);
2003 if (bfd_ardata (abfd) == (struct artdata *) NULL)
2004 goto error_ret_restore;
2006 /* Already cleared by bfd_zalloc above.
2007 bfd_ardata (abfd)->cache = NULL;
2008 bfd_ardata (abfd)->archive_head = NULL;
2009 bfd_ardata (abfd)->symdefs = NULL;
2010 bfd_ardata (abfd)->extended_names = NULL;
2011 bfd_ardata (abfd)->extended_names_size = 0; */
2012 bfd_ardata (abfd)->first_file_filepos = bfd_scan_vma (hdr.firstmemoff,
2013 (const char **) NULL,
2014 10);
2016 amt = SIZEOF_AR_FILE_HDR_BIG;
2017 bfd_ardata (abfd)->tdata = bfd_zalloc (abfd, amt);
2018 if (bfd_ardata (abfd)->tdata == NULL)
2019 goto error_ret;
2021 memcpy (bfd_ardata (abfd)->tdata, &hdr, SIZEOF_AR_FILE_HDR_BIG);
2023 if (! xcoff64_slurp_armap (abfd))
2025 error_ret:
2026 bfd_release (abfd, bfd_ardata (abfd));
2027 error_ret_restore:
2028 bfd_ardata (abfd) = tdata_hold;
2029 return NULL;
2032 return abfd->xvec;
2036 /* Open the next element in an XCOFF archive. */
2038 static bfd *
2039 xcoff64_openr_next_archived_file (archive, last_file)
2040 bfd *archive;
2041 bfd *last_file;
2043 bfd_vma filestart;
2045 if ((xcoff_ardata (archive) == NULL)
2046 || ! xcoff_big_format_p (archive))
2048 bfd_set_error (bfd_error_invalid_operation);
2049 return NULL;
2052 if (last_file == NULL)
2054 filestart = bfd_ardata (archive)->first_file_filepos;
2056 else
2058 filestart = bfd_scan_vma (arch_xhdr_big (last_file)->nextoff,
2059 (const char **) NULL, 10);
2062 if (filestart == 0
2063 || filestart == bfd_scan_vma (xcoff_ardata_big (archive)->memoff,
2064 (const char **) NULL, 10)
2065 || filestart == bfd_scan_vma (xcoff_ardata_big (archive)->symoff,
2066 (const char **) NULL, 10))
2068 bfd_set_error (bfd_error_no_more_archived_files);
2069 return NULL;
2072 return _bfd_get_elt_at_filepos (archive, (file_ptr) filestart);
2075 /* We can't use the usual coff_sizeof_headers routine, because AIX
2076 always uses an a.out header. */
2078 static int
2079 xcoff64_sizeof_headers (bfd *abfd,
2080 struct bfd_link_info *info ATTRIBUTE_UNUSED)
2082 int size;
2084 size = bfd_coff_filhsz (abfd);
2086 /* Don't think the small aout header can be used since some of the
2087 old elements have been reordered past the end of the old coff
2088 small aout size. */
2090 if (xcoff_data (abfd)->full_aouthdr)
2091 size += bfd_coff_aoutsz (abfd);
2093 size += abfd->section_count * bfd_coff_scnhsz (abfd);
2094 return size;
2099 static asection *
2100 xcoff64_create_csect_from_smclas (abfd, aux, symbol_name)
2101 bfd *abfd;
2102 union internal_auxent *aux;
2103 const char *symbol_name;
2105 asection *return_value = NULL;
2107 /* Changes from 32 :
2108 .sv == 8, is only for 32 bit programs
2109 .ti == 12 and .tb == 13 are now reserved. */
2110 static const char *names[19] =
2112 ".pr", ".ro", ".db", ".tc", ".ua", ".rw", ".gl", ".xo",
2113 NULL, ".bs", ".ds", ".uc", NULL, NULL, NULL, ".tc0",
2114 ".td", ".sv64", ".sv3264"
2117 if ((19 >= aux->x_csect.x_smclas)
2118 && (NULL != names[aux->x_csect.x_smclas]))
2121 return_value = bfd_make_section_anyway
2122 (abfd, names[aux->x_csect.x_smclas]);
2125 else
2127 (*_bfd_error_handler)
2128 (_("%B: symbol `%s' has unrecognized smclas %d"),
2129 abfd, symbol_name, aux->x_csect.x_smclas);
2130 bfd_set_error (bfd_error_bad_value);
2133 return return_value;
2136 static bfd_boolean
2137 xcoff64_is_lineno_count_overflow (abfd, value)
2138 bfd *abfd ATTRIBUTE_UNUSED;
2139 bfd_vma value ATTRIBUTE_UNUSED;
2141 return FALSE;
2144 static bfd_boolean
2145 xcoff64_is_reloc_count_overflow (abfd, value)
2146 bfd *abfd ATTRIBUTE_UNUSED;
2147 bfd_vma value ATTRIBUTE_UNUSED;
2149 return FALSE;
2152 static bfd_vma
2153 xcoff64_loader_symbol_offset (abfd, ldhdr)
2154 bfd *abfd ATTRIBUTE_UNUSED;
2155 struct internal_ldhdr *ldhdr;
2157 return (ldhdr->l_symoff);
2160 static bfd_vma
2161 xcoff64_loader_reloc_offset (abfd, ldhdr)
2162 bfd *abfd ATTRIBUTE_UNUSED;
2163 struct internal_ldhdr *ldhdr;
2165 return (ldhdr->l_rldoff);
2168 static bfd_boolean
2169 xcoff64_bad_format_hook (abfd, filehdr)
2170 bfd * abfd;
2171 PTR filehdr;
2173 struct internal_filehdr *internal_f = (struct internal_filehdr *) filehdr;
2175 /* Check flavor first. */
2176 if (bfd_get_flavour (abfd) != bfd_target_xcoff_flavour)
2177 return FALSE;
2179 if (bfd_xcoff_magic_number (abfd) != internal_f->f_magic)
2180 return FALSE;
2182 return TRUE;
2185 static bfd_boolean
2186 xcoff64_generate_rtinit (abfd, init, fini, rtld)
2187 bfd *abfd;
2188 const char *init;
2189 const char *fini;
2190 bfd_boolean rtld;
2192 bfd_byte filehdr_ext[FILHSZ];
2193 bfd_byte scnhdr_ext[SCNHSZ * 3];
2194 bfd_byte syment_ext[SYMESZ * 10];
2195 bfd_byte reloc_ext[RELSZ * 3];
2196 bfd_byte *data_buffer;
2197 bfd_size_type data_buffer_size;
2198 bfd_byte *string_table, *st_tmp;
2199 bfd_size_type string_table_size;
2200 bfd_vma val;
2201 size_t initsz, finisz;
2202 struct internal_filehdr filehdr;
2203 struct internal_scnhdr text_scnhdr;
2204 struct internal_scnhdr data_scnhdr;
2205 struct internal_scnhdr bss_scnhdr;
2206 struct internal_syment syment;
2207 union internal_auxent auxent;
2208 struct internal_reloc reloc;
2210 char *text_name = ".text";
2211 char *data_name = ".data";
2212 char *bss_name = ".bss";
2213 char *rtinit_name = "__rtinit";
2214 char *rtld_name = "__rtld";
2216 if (! bfd_xcoff_rtinit_size (abfd))
2217 return FALSE;
2219 initsz = (init == NULL ? 0 : 1 + strlen (init));
2220 finisz = (fini == NULL ? 0 : 1 + strlen (fini));
2222 /* File header. */
2223 memset (filehdr_ext, 0, FILHSZ);
2224 memset (&filehdr, 0, sizeof (struct internal_filehdr));
2225 filehdr.f_magic = bfd_xcoff_magic_number (abfd);
2226 filehdr.f_nscns = 3;
2227 filehdr.f_timdat = 0;
2228 filehdr.f_nsyms = 0; /* at least 6, no more than 8 */
2229 filehdr.f_symptr = 0; /* set below */
2230 filehdr.f_opthdr = 0;
2231 filehdr.f_flags = 0;
2233 /* Section headers. */
2234 memset (scnhdr_ext, 0, 3 * SCNHSZ);
2236 /* Text. */
2237 memset (&text_scnhdr, 0, sizeof (struct internal_scnhdr));
2238 memcpy (text_scnhdr.s_name, text_name, strlen (text_name));
2239 text_scnhdr.s_paddr = 0;
2240 text_scnhdr.s_vaddr = 0;
2241 text_scnhdr.s_size = 0;
2242 text_scnhdr.s_scnptr = 0;
2243 text_scnhdr.s_relptr = 0;
2244 text_scnhdr.s_lnnoptr = 0;
2245 text_scnhdr.s_nreloc = 0;
2246 text_scnhdr.s_nlnno = 0;
2247 text_scnhdr.s_flags = STYP_TEXT;
2249 /* Data. */
2250 memset (&data_scnhdr, 0, sizeof (struct internal_scnhdr));
2251 memcpy (data_scnhdr.s_name, data_name, strlen (data_name));
2252 data_scnhdr.s_paddr = 0;
2253 data_scnhdr.s_vaddr = 0;
2254 data_scnhdr.s_size = 0; /* set below */
2255 data_scnhdr.s_scnptr = FILHSZ + 3 * SCNHSZ;
2256 data_scnhdr.s_relptr = 0; /* set below */
2257 data_scnhdr.s_lnnoptr = 0;
2258 data_scnhdr.s_nreloc = 0; /* either 1 or 2 */
2259 data_scnhdr.s_nlnno = 0;
2260 data_scnhdr.s_flags = STYP_DATA;
2262 /* Bss. */
2263 memset (&bss_scnhdr, 0, sizeof (struct internal_scnhdr));
2264 memcpy (bss_scnhdr.s_name, bss_name, strlen (bss_name));
2265 bss_scnhdr.s_paddr = 0; /* set below */
2266 bss_scnhdr.s_vaddr = 0; /* set below */
2267 bss_scnhdr.s_size = 0; /* set below */
2268 bss_scnhdr.s_scnptr = 0;
2269 bss_scnhdr.s_relptr = 0;
2270 bss_scnhdr.s_lnnoptr = 0;
2271 bss_scnhdr.s_nreloc = 0;
2272 bss_scnhdr.s_nlnno = 0;
2273 bss_scnhdr.s_flags = STYP_BSS;
2275 /* .data
2276 0x0000 0x00000000 : rtl
2277 0x0004 0x00000000 :
2278 0x0008 0x00000018 : offset to init, or 0
2279 0x000C 0x00000038 : offset to fini, or 0
2280 0x0010 0x00000010 : size of descriptor
2281 0x0014 0x00000000 : pad
2282 0x0018 0x00000000 : init, needs a reloc
2283 0x001C 0x00000000 :
2284 0x0020 0x00000058 : offset to init name
2285 0x0024 0x00000000 : flags, padded to a word
2286 0x0028 0x00000000 : empty init
2287 0x002C 0x00000000 :
2288 0x0030 0x00000000 :
2289 0x0034 0x00000000 :
2290 0x0038 0x00000000 : fini, needs a reloc
2291 0x003C 0x00000000 :
2292 0x0040 0x00000??? : offset to fini name
2293 0x0044 0x00000000 : flags, padded to a word
2294 0x0048 0x00000000 : empty fini
2295 0x004C 0x00000000 :
2296 0x0050 0x00000000 :
2297 0x0054 0x00000000 :
2298 0x0058 init name
2299 0x0058 + initsz fini name */
2301 data_buffer_size = 0x0058 + initsz + finisz;
2302 data_buffer_size = (data_buffer_size + 7) &~ (bfd_size_type) 7;
2303 data_buffer = NULL;
2304 data_buffer = (bfd_byte *) bfd_zmalloc (data_buffer_size);
2305 if (data_buffer == NULL)
2306 return FALSE;
2308 if (initsz)
2310 val = 0x18;
2311 bfd_put_32 (abfd, val, &data_buffer[0x08]);
2312 val = 0x58;
2313 bfd_put_32 (abfd, val, &data_buffer[0x20]);
2314 memcpy (&data_buffer[val], init, initsz);
2317 if (finisz)
2319 val = 0x38;
2320 bfd_put_32 (abfd, val, &data_buffer[0x0C]);
2321 val = 0x58 + initsz;
2322 bfd_put_32 (abfd, val, &data_buffer[0x40]);
2323 memcpy (&data_buffer[val], fini, finisz);
2326 val = 0x10;
2327 bfd_put_32 (abfd, val, &data_buffer[0x10]);
2328 data_scnhdr.s_size = data_buffer_size;
2329 bss_scnhdr.s_paddr = bss_scnhdr.s_vaddr = data_scnhdr.s_size;
2331 /* String table. */
2332 string_table_size = 4;
2333 string_table_size += strlen (data_name) + 1;
2334 string_table_size += strlen (rtinit_name) + 1;
2335 string_table_size += initsz;
2336 string_table_size += finisz;
2337 if (rtld)
2338 string_table_size += strlen (rtld_name) + 1;
2340 string_table = (bfd_byte *) bfd_zmalloc (string_table_size);
2341 if (string_table == NULL)
2342 return FALSE;
2344 val = string_table_size;
2345 bfd_put_32 (abfd, val, &string_table[0]);
2346 st_tmp = string_table + 4;
2348 /* symbols
2349 0. .data csect
2350 2. __rtinit
2351 4. init function
2352 6. fini function
2353 8. __rtld */
2354 memset (syment_ext, 0, 10 * SYMESZ);
2355 memset (reloc_ext, 0, 3 * RELSZ);
2357 /* .data csect */
2358 memset (&syment, 0, sizeof (struct internal_syment));
2359 memset (&auxent, 0, sizeof (union internal_auxent));
2361 syment._n._n_n._n_offset = st_tmp - string_table;
2362 memcpy (st_tmp, data_name, strlen (data_name));
2363 st_tmp += strlen (data_name) + 1;
2365 syment.n_scnum = 2;
2366 syment.n_sclass = C_HIDEXT;
2367 syment.n_numaux = 1;
2368 auxent.x_csect.x_scnlen.l = data_buffer_size;
2369 auxent.x_csect.x_smtyp = 3 << 3 | XTY_SD;
2370 auxent.x_csect.x_smclas = XMC_RW;
2371 bfd_coff_swap_sym_out (abfd, &syment,
2372 &syment_ext[filehdr.f_nsyms * SYMESZ]);
2373 bfd_coff_swap_aux_out (abfd, &auxent, syment.n_type, syment.n_sclass, 0,
2374 syment.n_numaux,
2375 &syment_ext[(filehdr.f_nsyms + 1) * SYMESZ]);
2376 filehdr.f_nsyms += 2;
2378 /* __rtinit */
2379 memset (&syment, 0, sizeof (struct internal_syment));
2380 memset (&auxent, 0, sizeof (union internal_auxent));
2381 syment._n._n_n._n_offset = st_tmp - string_table;
2382 memcpy (st_tmp, rtinit_name, strlen (rtinit_name));
2383 st_tmp += strlen (rtinit_name) + 1;
2385 syment.n_scnum = 2;
2386 syment.n_sclass = C_EXT;
2387 syment.n_numaux = 1;
2388 auxent.x_csect.x_smtyp = XTY_LD;
2389 auxent.x_csect.x_smclas = XMC_RW;
2390 bfd_coff_swap_sym_out (abfd, &syment,
2391 &syment_ext[filehdr.f_nsyms * SYMESZ]);
2392 bfd_coff_swap_aux_out (abfd, &auxent, syment.n_type, syment.n_sclass, 0,
2393 syment.n_numaux,
2394 &syment_ext[(filehdr.f_nsyms + 1) * SYMESZ]);
2395 filehdr.f_nsyms += 2;
2397 /* Init. */
2398 if (initsz)
2400 memset (&syment, 0, sizeof (struct internal_syment));
2401 memset (&auxent, 0, sizeof (union internal_auxent));
2403 syment._n._n_n._n_offset = st_tmp - string_table;
2404 memcpy (st_tmp, init, initsz);
2405 st_tmp += initsz;
2407 syment.n_sclass = C_EXT;
2408 syment.n_numaux = 1;
2409 bfd_coff_swap_sym_out (abfd, &syment,
2410 &syment_ext[filehdr.f_nsyms * SYMESZ]);
2411 bfd_coff_swap_aux_out (abfd, &auxent, syment.n_type, syment.n_sclass, 0,
2412 syment.n_numaux,
2413 &syment_ext[(filehdr.f_nsyms + 1) * SYMESZ]);
2414 /* Reloc. */
2415 memset (&reloc, 0, sizeof (struct internal_reloc));
2416 reloc.r_vaddr = 0x0018;
2417 reloc.r_symndx = filehdr.f_nsyms;
2418 reloc.r_type = R_POS;
2419 reloc.r_size = 63;
2420 bfd_coff_swap_reloc_out (abfd, &reloc, &reloc_ext[0]);
2422 filehdr.f_nsyms += 2;
2423 data_scnhdr.s_nreloc += 1;
2426 /* Finit. */
2427 if (finisz)
2429 memset (&syment, 0, sizeof (struct internal_syment));
2430 memset (&auxent, 0, sizeof (union internal_auxent));
2432 syment._n._n_n._n_offset = st_tmp - string_table;
2433 memcpy (st_tmp, fini, finisz);
2434 st_tmp += finisz;
2436 syment.n_sclass = C_EXT;
2437 syment.n_numaux = 1;
2438 bfd_coff_swap_sym_out (abfd, &syment,
2439 &syment_ext[filehdr.f_nsyms * SYMESZ]);
2440 bfd_coff_swap_aux_out (abfd, &auxent, syment.n_type, syment.n_sclass, 0,
2441 syment.n_numaux,
2442 &syment_ext[(filehdr.f_nsyms + 1) * SYMESZ]);
2444 /* Reloc. */
2445 memset (&reloc, 0, sizeof (struct internal_reloc));
2446 reloc.r_vaddr = 0x0038;
2447 reloc.r_symndx = filehdr.f_nsyms;
2448 reloc.r_type = R_POS;
2449 reloc.r_size = 63;
2450 bfd_coff_swap_reloc_out (abfd, &reloc,
2451 &reloc_ext[data_scnhdr.s_nreloc * RELSZ]);
2453 filehdr.f_nsyms += 2;
2454 data_scnhdr.s_nreloc += 1;
2457 if (rtld)
2459 memset (&syment, 0, sizeof (struct internal_syment));
2460 memset (&auxent, 0, sizeof (union internal_auxent));
2462 syment._n._n_n._n_offset = st_tmp - string_table;
2463 memcpy (st_tmp, rtld_name, strlen (rtld_name));
2464 st_tmp += strlen (rtld_name) + 1;
2466 syment.n_sclass = C_EXT;
2467 syment.n_numaux = 1;
2468 bfd_coff_swap_sym_out (abfd, &syment,
2469 &syment_ext[filehdr.f_nsyms * SYMESZ]);
2470 bfd_coff_swap_aux_out (abfd, &auxent, syment.n_type, syment.n_sclass, 0,
2471 syment.n_numaux,
2472 &syment_ext[(filehdr.f_nsyms + 1) * SYMESZ]);
2474 /* Reloc. */
2475 memset (&reloc, 0, sizeof (struct internal_reloc));
2476 reloc.r_vaddr = 0x0000;
2477 reloc.r_symndx = filehdr.f_nsyms;
2478 reloc.r_type = R_POS;
2479 reloc.r_size = 63;
2480 bfd_coff_swap_reloc_out (abfd, &reloc,
2481 &reloc_ext[data_scnhdr.s_nreloc * RELSZ]);
2483 filehdr.f_nsyms += 2;
2484 data_scnhdr.s_nreloc += 1;
2486 bss_scnhdr.s_size = 0;
2489 data_scnhdr.s_relptr = data_scnhdr.s_scnptr + data_buffer_size;
2490 filehdr.f_symptr = data_scnhdr.s_relptr + data_scnhdr.s_nreloc * RELSZ;
2492 bfd_coff_swap_filehdr_out (abfd, &filehdr, filehdr_ext);
2493 bfd_bwrite (filehdr_ext, FILHSZ, abfd);
2494 bfd_coff_swap_scnhdr_out (abfd, &text_scnhdr, &scnhdr_ext[SCNHSZ * 0]);
2495 bfd_coff_swap_scnhdr_out (abfd, &data_scnhdr, &scnhdr_ext[SCNHSZ * 1]);
2496 bfd_coff_swap_scnhdr_out (abfd, &bss_scnhdr, &scnhdr_ext[SCNHSZ * 2]);
2497 bfd_bwrite (scnhdr_ext, 3 * SCNHSZ, abfd);
2498 bfd_bwrite (data_buffer, data_buffer_size, abfd);
2499 bfd_bwrite (reloc_ext, data_scnhdr.s_nreloc * RELSZ, abfd);
2500 bfd_bwrite (syment_ext, filehdr.f_nsyms * SYMESZ, abfd);
2501 bfd_bwrite (string_table, string_table_size, abfd);
2503 free (data_buffer);
2504 data_buffer = NULL;
2506 return TRUE;
2509 /* The typical dynamic reloc. */
2511 static reloc_howto_type xcoff64_dynamic_reloc =
2512 HOWTO (0, /* type */
2513 0, /* rightshift */
2514 4, /* size (0 = byte, 1 = short, 2 = long) */
2515 64, /* bitsize */
2516 FALSE, /* pc_relative */
2517 0, /* bitpos */
2518 complain_overflow_bitfield, /* complain_on_overflow */
2519 0, /* special_function */
2520 "R_POS", /* name */
2521 TRUE, /* partial_inplace */
2522 MINUS_ONE, /* src_mask */
2523 MINUS_ONE, /* dst_mask */
2524 FALSE); /* pcrel_offset */
2526 static unsigned long xcoff64_glink_code[10] =
2528 0xe9820000, /* ld r12,0(r2) */
2529 0xf8410028, /* std r2,40(r1) */
2530 0xe80c0000, /* ld r0,0(r12) */
2531 0xe84c0008, /* ld r0,8(r12) */
2532 0x7c0903a6, /* mtctr r0 */
2533 0x4e800420, /* bctr */
2534 0x00000000, /* start of traceback table */
2535 0x000ca000, /* traceback table */
2536 0x00000000, /* traceback table */
2537 0x00000018, /* ??? */
2540 static const struct xcoff_backend_data_rec bfd_xcoff_backend_data =
2542 { /* COFF backend, defined in libcoff.h. */
2543 _bfd_xcoff64_swap_aux_in,
2544 _bfd_xcoff64_swap_sym_in,
2545 _bfd_xcoff64_swap_lineno_in,
2546 _bfd_xcoff64_swap_aux_out,
2547 _bfd_xcoff64_swap_sym_out,
2548 _bfd_xcoff64_swap_lineno_out,
2549 xcoff64_swap_reloc_out,
2550 coff_swap_filehdr_out,
2551 coff_swap_aouthdr_out,
2552 coff_swap_scnhdr_out,
2553 FILHSZ,
2554 AOUTSZ,
2555 SCNHSZ,
2556 SYMESZ,
2557 AUXESZ,
2558 RELSZ,
2559 LINESZ,
2560 FILNMLEN,
2561 TRUE, /* _bfd_coff_long_filenames */
2562 XCOFF_NO_LONG_SECTION_NAMES, /* _bfd_coff_long_section_names */
2563 3, /* _bfd_coff_default_section_alignment_power */
2564 TRUE, /* _bfd_coff_force_symnames_in_strings */
2565 4, /* _bfd_coff_debug_string_prefix_length */
2566 coff_swap_filehdr_in,
2567 coff_swap_aouthdr_in,
2568 coff_swap_scnhdr_in,
2569 xcoff64_swap_reloc_in,
2570 xcoff64_bad_format_hook,
2571 coff_set_arch_mach_hook,
2572 coff_mkobject_hook,
2573 styp_to_sec_flags,
2574 coff_set_alignment_hook,
2575 coff_slurp_symbol_table,
2576 symname_in_debug_hook,
2577 coff_pointerize_aux_hook,
2578 coff_print_aux,
2579 dummy_reloc16_extra_cases,
2580 dummy_reloc16_estimate,
2581 NULL, /* bfd_coff_symbol_classification */
2582 coff_compute_section_file_positions,
2583 NULL, /* _bfd_coff_start_final_link */
2584 xcoff64_ppc_relocate_section,
2585 coff_rtype_to_howto,
2586 NULL, /* _bfd_coff_adjust_symndx */
2587 _bfd_generic_link_add_one_symbol,
2588 coff_link_output_has_begun,
2589 coff_final_link_postscript,
2590 NULL /* print_pdata. */
2593 0x01EF, /* magic number */
2594 bfd_arch_powerpc,
2595 bfd_mach_ppc_620,
2597 /* Function pointers to xcoff specific swap routines. */
2598 xcoff64_swap_ldhdr_in,
2599 xcoff64_swap_ldhdr_out,
2600 xcoff64_swap_ldsym_in,
2601 xcoff64_swap_ldsym_out,
2602 xcoff64_swap_ldrel_in,
2603 xcoff64_swap_ldrel_out,
2605 /* Sizes. */
2606 LDHDRSZ,
2607 LDSYMSZ,
2608 LDRELSZ,
2609 24, /* _xcoff_function_descriptor_size */
2610 0, /* _xcoff_small_aout_header_size */
2612 /* Versions. */
2613 2, /* _xcoff_ldhdr_version */
2615 _bfd_xcoff64_put_symbol_name,
2616 _bfd_xcoff64_put_ldsymbol_name,
2617 &xcoff64_dynamic_reloc,
2618 xcoff64_create_csect_from_smclas,
2620 /* Lineno and reloc count overflow. */
2621 xcoff64_is_lineno_count_overflow,
2622 xcoff64_is_reloc_count_overflow,
2624 xcoff64_loader_symbol_offset,
2625 xcoff64_loader_reloc_offset,
2627 /* glink. */
2628 &xcoff64_glink_code[0],
2629 40, /* _xcoff_glink_size */
2631 /* rtinit. */
2632 88, /* _xcoff_rtinit_size */
2633 xcoff64_generate_rtinit,
2636 /* The transfer vector that leads the outside world to all of the above. */
2637 const bfd_target rs6000coff64_vec =
2639 "aixcoff64-rs6000",
2640 bfd_target_xcoff_flavour,
2641 BFD_ENDIAN_BIG, /* data byte order is big */
2642 BFD_ENDIAN_BIG, /* header byte order is big */
2644 (HAS_RELOC | EXEC_P | HAS_LINENO | HAS_DEBUG | DYNAMIC
2645 | HAS_SYMS | HAS_LOCALS | WP_TEXT),
2647 SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_RELOC | SEC_CODE | SEC_DATA,
2648 0, /* leading char */
2649 '/', /* ar_pad_char */
2650 15, /* ar_max_namelen */
2652 /* data */
2653 bfd_getb64,
2654 bfd_getb_signed_64,
2655 bfd_putb64,
2656 bfd_getb32,
2657 bfd_getb_signed_32,
2658 bfd_putb32,
2659 bfd_getb16,
2660 bfd_getb_signed_16,
2661 bfd_putb16,
2663 /* hdrs */
2664 bfd_getb64,
2665 bfd_getb_signed_64,
2666 bfd_putb64,
2667 bfd_getb32,
2668 bfd_getb_signed_32,
2669 bfd_putb32,
2670 bfd_getb16,
2671 bfd_getb_signed_16,
2672 bfd_putb16,
2674 { /* bfd_check_format */
2675 _bfd_dummy_target,
2676 coff_object_p,
2677 xcoff64_archive_p,
2678 CORE_FILE_P
2681 { /* bfd_set_format */
2682 bfd_false,
2683 coff_mkobject,
2684 _bfd_generic_mkarchive,
2685 bfd_false
2688 {/* bfd_write_contents */
2689 bfd_false,
2690 xcoff64_write_object_contents,
2691 _bfd_xcoff_write_archive_contents,
2692 bfd_false
2695 /* Generic */
2696 bfd_true,
2697 bfd_true,
2698 coff_new_section_hook,
2699 _bfd_generic_get_section_contents,
2700 _bfd_generic_get_section_contents_in_window,
2702 /* Copy */
2703 _bfd_xcoff_copy_private_bfd_data,
2704 ((bfd_boolean (*) (bfd *, bfd *)) bfd_true),
2705 _bfd_generic_init_private_section_data,
2706 ((bfd_boolean (*) (bfd *, asection *, bfd *, asection *)) bfd_true),
2707 ((bfd_boolean (*) (bfd *, asymbol *, bfd *, asymbol *)) bfd_true),
2708 ((bfd_boolean (*) (bfd *, bfd *)) bfd_true),
2709 ((bfd_boolean (*) (bfd *, flagword)) bfd_true),
2710 ((bfd_boolean (*) (bfd *, void * )) bfd_true),
2712 /* Core */
2713 coff_core_file_failing_command,
2714 coff_core_file_failing_signal,
2715 coff_core_file_matches_executable_p,
2717 /* Archive */
2718 xcoff64_slurp_armap,
2719 bfd_false,
2720 ((bfd_boolean (*) (bfd *, char **, bfd_size_type *, const char **)) bfd_false),
2721 bfd_dont_truncate_arname,
2722 _bfd_xcoff_write_armap,
2723 _bfd_xcoff_read_ar_hdr,
2724 xcoff64_openr_next_archived_file,
2725 _bfd_generic_get_elt_at_index,
2726 _bfd_xcoff_stat_arch_elt,
2727 bfd_true,
2729 /* Symbols */
2730 coff_get_symtab_upper_bound,
2731 coff_canonicalize_symtab,
2732 coff_make_empty_symbol,
2733 coff_print_symbol,
2734 coff_get_symbol_info,
2735 _bfd_xcoff_is_local_label_name,
2736 coff_bfd_is_target_special_symbol,
2737 coff_get_lineno,
2738 coff_find_nearest_line,
2739 _bfd_generic_find_line,
2740 coff_find_inliner_info,
2741 coff_bfd_make_debug_symbol,
2742 _bfd_generic_read_minisymbols,
2743 _bfd_generic_minisymbol_to_symbol,
2745 /* Reloc */
2746 coff_get_reloc_upper_bound,
2747 coff_canonicalize_reloc,
2748 xcoff64_reloc_type_lookup,
2749 xcoff64_reloc_name_lookup,
2751 /* Write */
2752 coff_set_arch_mach,
2753 coff_set_section_contents,
2755 /* Link */
2756 xcoff64_sizeof_headers,
2757 bfd_generic_get_relocated_section_contents,
2758 bfd_generic_relax_section,
2759 _bfd_xcoff_bfd_link_hash_table_create,
2760 _bfd_generic_link_hash_table_free,
2761 _bfd_xcoff_bfd_link_add_symbols,
2762 _bfd_generic_link_just_syms,
2763 _bfd_xcoff_bfd_final_link,
2764 _bfd_generic_link_split_section,
2765 bfd_generic_gc_sections,
2766 bfd_generic_merge_sections,
2767 bfd_generic_is_group_section,
2768 bfd_generic_discard_group,
2769 _bfd_generic_section_already_linked,
2771 /* Dynamic */
2772 _bfd_xcoff_get_dynamic_symtab_upper_bound,
2773 _bfd_xcoff_canonicalize_dynamic_symtab,
2774 _bfd_nodynamic_get_synthetic_symtab,
2775 _bfd_xcoff_get_dynamic_reloc_upper_bound,
2776 _bfd_xcoff_canonicalize_dynamic_reloc,
2778 /* Opposite endian version, none exists */
2779 NULL,
2781 (void *) &bfd_xcoff_backend_data,
2784 extern const bfd_target *xcoff64_core_p
2785 PARAMS ((bfd *));
2786 extern bfd_boolean xcoff64_core_file_matches_executable_p
2787 PARAMS ((bfd *, bfd *));
2788 extern char *xcoff64_core_file_failing_command
2789 PARAMS ((bfd *));
2790 extern int xcoff64_core_file_failing_signal
2791 PARAMS ((bfd *));
2793 /* AIX 5 */
2794 static const struct xcoff_backend_data_rec bfd_xcoff_aix5_backend_data =
2796 { /* COFF backend, defined in libcoff.h. */
2797 _bfd_xcoff64_swap_aux_in,
2798 _bfd_xcoff64_swap_sym_in,
2799 _bfd_xcoff64_swap_lineno_in,
2800 _bfd_xcoff64_swap_aux_out,
2801 _bfd_xcoff64_swap_sym_out,
2802 _bfd_xcoff64_swap_lineno_out,
2803 xcoff64_swap_reloc_out,
2804 coff_swap_filehdr_out,
2805 coff_swap_aouthdr_out,
2806 coff_swap_scnhdr_out,
2807 FILHSZ,
2808 AOUTSZ,
2809 SCNHSZ,
2810 SYMESZ,
2811 AUXESZ,
2812 RELSZ,
2813 LINESZ,
2814 FILNMLEN,
2815 TRUE, /* _bfd_coff_long_filenames */
2816 XCOFF_NO_LONG_SECTION_NAMES, /* _bfd_coff_long_section_names */
2817 3, /* _bfd_coff_default_section_alignment_power */
2818 TRUE, /* _bfd_coff_force_symnames_in_strings */
2819 4, /* _bfd_coff_debug_string_prefix_length */
2820 coff_swap_filehdr_in,
2821 coff_swap_aouthdr_in,
2822 coff_swap_scnhdr_in,
2823 xcoff64_swap_reloc_in,
2824 xcoff64_bad_format_hook,
2825 coff_set_arch_mach_hook,
2826 coff_mkobject_hook,
2827 styp_to_sec_flags,
2828 coff_set_alignment_hook,
2829 coff_slurp_symbol_table,
2830 symname_in_debug_hook,
2831 coff_pointerize_aux_hook,
2832 coff_print_aux,
2833 dummy_reloc16_extra_cases,
2834 dummy_reloc16_estimate,
2835 NULL, /* bfd_coff_sym_is_global */
2836 coff_compute_section_file_positions,
2837 NULL, /* _bfd_coff_start_final_link */
2838 xcoff64_ppc_relocate_section,
2839 coff_rtype_to_howto,
2840 NULL, /* _bfd_coff_adjust_symndx */
2841 _bfd_generic_link_add_one_symbol,
2842 coff_link_output_has_begun,
2843 coff_final_link_postscript,
2844 NULL /* print_pdata. */
2847 U64_TOCMAGIC, /* magic number */
2848 bfd_arch_powerpc,
2849 bfd_mach_ppc_620,
2851 /* Function pointers to xcoff specific swap routines. */
2852 xcoff64_swap_ldhdr_in,
2853 xcoff64_swap_ldhdr_out,
2854 xcoff64_swap_ldsym_in,
2855 xcoff64_swap_ldsym_out,
2856 xcoff64_swap_ldrel_in,
2857 xcoff64_swap_ldrel_out,
2859 /* Sizes. */
2860 LDHDRSZ,
2861 LDSYMSZ,
2862 LDRELSZ,
2863 24, /* _xcoff_function_descriptor_size */
2864 0, /* _xcoff_small_aout_header_size */
2865 /* Versions. */
2866 2, /* _xcoff_ldhdr_version */
2868 _bfd_xcoff64_put_symbol_name,
2869 _bfd_xcoff64_put_ldsymbol_name,
2870 &xcoff64_dynamic_reloc,
2871 xcoff64_create_csect_from_smclas,
2873 /* Lineno and reloc count overflow. */
2874 xcoff64_is_lineno_count_overflow,
2875 xcoff64_is_reloc_count_overflow,
2877 xcoff64_loader_symbol_offset,
2878 xcoff64_loader_reloc_offset,
2880 /* glink. */
2881 &xcoff64_glink_code[0],
2882 40, /* _xcoff_glink_size */
2884 /* rtinit. */
2885 88, /* _xcoff_rtinit_size */
2886 xcoff64_generate_rtinit,
2889 /* The transfer vector that leads the outside world to all of the above. */
2890 const bfd_target aix5coff64_vec =
2892 "aix5coff64-rs6000",
2893 bfd_target_xcoff_flavour,
2894 BFD_ENDIAN_BIG, /* data byte order is big */
2895 BFD_ENDIAN_BIG, /* header byte order is big */
2897 (HAS_RELOC | EXEC_P | HAS_LINENO | HAS_DEBUG | DYNAMIC
2898 | HAS_SYMS | HAS_LOCALS | WP_TEXT),
2900 SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_RELOC | SEC_CODE | SEC_DATA,
2901 0, /* leading char */
2902 '/', /* ar_pad_char */
2903 15, /* ar_max_namelen */
2905 /* data */
2906 bfd_getb64,
2907 bfd_getb_signed_64,
2908 bfd_putb64,
2909 bfd_getb32,
2910 bfd_getb_signed_32,
2911 bfd_putb32,
2912 bfd_getb16,
2913 bfd_getb_signed_16,
2914 bfd_putb16,
2916 /* hdrs */
2917 bfd_getb64,
2918 bfd_getb_signed_64,
2919 bfd_putb64,
2920 bfd_getb32,
2921 bfd_getb_signed_32,
2922 bfd_putb32,
2923 bfd_getb16,
2924 bfd_getb_signed_16,
2925 bfd_putb16,
2927 { /* bfd_check_format */
2928 _bfd_dummy_target,
2929 coff_object_p,
2930 xcoff64_archive_p,
2931 xcoff64_core_p
2934 { /* bfd_set_format */
2935 bfd_false,
2936 coff_mkobject,
2937 _bfd_generic_mkarchive,
2938 bfd_false
2941 {/* bfd_write_contents */
2942 bfd_false,
2943 xcoff64_write_object_contents,
2944 _bfd_xcoff_write_archive_contents,
2945 bfd_false
2948 /* Generic */
2949 bfd_true,
2950 bfd_true,
2951 coff_new_section_hook,
2952 _bfd_generic_get_section_contents,
2953 _bfd_generic_get_section_contents_in_window,
2955 /* Copy */
2956 _bfd_xcoff_copy_private_bfd_data,
2957 ((bfd_boolean (*) (bfd *, bfd *)) bfd_true),
2958 _bfd_generic_init_private_section_data,
2959 ((bfd_boolean (*) (bfd *, asection *, bfd *, asection *)) bfd_true),
2960 ((bfd_boolean (*) (bfd *, asymbol *, bfd *, asymbol *)) bfd_true),
2961 ((bfd_boolean (*) (bfd *, bfd *)) bfd_true),
2962 ((bfd_boolean (*) (bfd *, flagword)) bfd_true),
2963 ((bfd_boolean (*) (bfd *, void * )) bfd_true),
2965 /* Core */
2966 xcoff64_core_file_failing_command,
2967 xcoff64_core_file_failing_signal,
2968 xcoff64_core_file_matches_executable_p,
2970 /* Archive */
2971 xcoff64_slurp_armap,
2972 bfd_false,
2973 ((bfd_boolean (*) (bfd *, char **, bfd_size_type *, const char **)) bfd_false),
2974 bfd_dont_truncate_arname,
2975 _bfd_xcoff_write_armap,
2976 _bfd_xcoff_read_ar_hdr,
2977 xcoff64_openr_next_archived_file,
2978 _bfd_generic_get_elt_at_index,
2979 _bfd_xcoff_stat_arch_elt,
2980 bfd_true,
2982 /* Symbols */
2983 coff_get_symtab_upper_bound,
2984 coff_canonicalize_symtab,
2985 coff_make_empty_symbol,
2986 coff_print_symbol,
2987 coff_get_symbol_info,
2988 _bfd_xcoff_is_local_label_name,
2989 coff_bfd_is_target_special_symbol,
2990 coff_get_lineno,
2991 coff_find_nearest_line,
2992 _bfd_generic_find_line,
2993 coff_find_inliner_info,
2994 coff_bfd_make_debug_symbol,
2995 _bfd_generic_read_minisymbols,
2996 _bfd_generic_minisymbol_to_symbol,
2998 /* Reloc */
2999 coff_get_reloc_upper_bound,
3000 coff_canonicalize_reloc,
3001 xcoff64_reloc_type_lookup,
3002 xcoff64_reloc_name_lookup,
3004 /* Write */
3005 coff_set_arch_mach,
3006 coff_set_section_contents,
3008 /* Link */
3009 xcoff64_sizeof_headers,
3010 bfd_generic_get_relocated_section_contents,
3011 bfd_generic_relax_section,
3012 _bfd_xcoff_bfd_link_hash_table_create,
3013 _bfd_generic_link_hash_table_free,
3014 _bfd_xcoff_bfd_link_add_symbols,
3015 _bfd_generic_link_just_syms,
3016 _bfd_xcoff_bfd_final_link,
3017 _bfd_generic_link_split_section,
3018 bfd_generic_gc_sections,
3019 bfd_generic_merge_sections,
3020 bfd_generic_is_group_section,
3021 bfd_generic_discard_group,
3022 _bfd_generic_section_already_linked,
3024 /* Dynamic */
3025 _bfd_xcoff_get_dynamic_symtab_upper_bound,
3026 _bfd_xcoff_canonicalize_dynamic_symtab,
3027 _bfd_nodynamic_get_synthetic_symtab,
3028 _bfd_xcoff_get_dynamic_reloc_upper_bound,
3029 _bfd_xcoff_canonicalize_dynamic_reloc,
3031 /* Opposite endian version, none exists. */
3032 NULL,
3034 (void *) & bfd_xcoff_aix5_backend_data,