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