1/* BFD back-end for IBM RS/6000 "XCOFF" files.
2   Copyright 1990-1999, 2000, 2001, 2002, 2003, 2004
3   Free Software Foundation, Inc.
4   FIXME: Can someone provide a transliteration of this name into ASCII?
5   Using the following chars caused a compiler warning on HIUX (so I replaced
6   them with octal escapes), and isn't useful without an understanding of what
7   character set it is.
8   Written by Metin G. Ozisik, Mimi Ph\373\364ng-Th\345o V\365,
9     and John Gilmore.
10   Archive support from Damon A. Permezel.
11   Contributed by IBM Corporation and Cygnus Support.
12
13This file is part of BFD, the Binary File Descriptor library.
14
15This program is free software; you can redistribute it and/or modify
16it under the terms of the GNU General Public License as published by
17the Free Software Foundation; either version 2 of the License, or
18(at your option) any later version.
19
20This program is distributed in the hope that it will be useful,
21but WITHOUT ANY WARRANTY; without even the implied warranty of
22MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
23GNU General Public License for more details.
24
25You should have received a copy of the GNU General Public License
26along with this program; if not, write to the Free Software
27Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
28
29#include "bfd.h"
30#include "sysdep.h"
31#include "bfdlink.h"
32#include "libbfd.h"
33#include "coff/internal.h"
34#include "coff/xcoff.h"
35#include "coff/rs6000.h"
36#include "libcoff.h"
37#include "libxcoff.h"
38
39extern bfd_boolean _bfd_xcoff_mkobject
40  PARAMS ((bfd *));
41extern bfd_boolean _bfd_xcoff_copy_private_bfd_data
42  PARAMS ((bfd *, bfd *));
43extern bfd_boolean _bfd_xcoff_is_local_label_name
44  PARAMS ((bfd *, const char *));
45extern reloc_howto_type *_bfd_xcoff_reloc_type_lookup
46  PARAMS ((bfd *, bfd_reloc_code_real_type));
47extern bfd_boolean _bfd_xcoff_slurp_armap
48  PARAMS ((bfd *));
49extern const bfd_target *_bfd_xcoff_archive_p
50  PARAMS ((bfd *));
51extern PTR _bfd_xcoff_read_ar_hdr
52  PARAMS ((bfd *));
53extern bfd *_bfd_xcoff_openr_next_archived_file
54  PARAMS ((bfd *, bfd *));
55extern int _bfd_xcoff_stat_arch_elt
56  PARAMS ((bfd *, struct stat *));
57extern bfd_boolean _bfd_xcoff_write_armap
58  PARAMS ((bfd *, unsigned int, struct orl *, unsigned int, int));
59extern bfd_boolean _bfd_xcoff_write_archive_contents
60  PARAMS ((bfd *));
61extern int _bfd_xcoff_sizeof_headers
62  PARAMS ((bfd *, bfd_boolean));
63extern void _bfd_xcoff_swap_sym_in
64  PARAMS ((bfd *, PTR, PTR));
65extern unsigned int _bfd_xcoff_swap_sym_out
66  PARAMS ((bfd *, PTR, PTR));
67extern void _bfd_xcoff_swap_aux_in
68  PARAMS ((bfd *, PTR, int, int, int, int, PTR));
69extern unsigned int _bfd_xcoff_swap_aux_out
70  PARAMS ((bfd *, PTR, int, int, int, int, PTR));
71static void xcoff_swap_reloc_in
72  PARAMS ((bfd *, PTR, PTR));
73static unsigned int xcoff_swap_reloc_out
74  PARAMS ((bfd *, PTR, PTR));
75
76/* Forward declare xcoff_rtype2howto for coffcode.h macro.  */
77void xcoff_rtype2howto
78  PARAMS ((arelent *, struct internal_reloc *));
79
80/* coffcode.h needs these to be defined.  */
81#define RS6000COFF_C 1
82
83#define SELECT_RELOC(internal, howto)					\
84  {									\
85    internal.r_type = howto->type;					\
86    internal.r_size =							\
87      ((howto->complain_on_overflow == complain_overflow_signed		\
88	? 0x80								\
89	: 0)								\
90       | (howto->bitsize - 1));						\
91  }
92
93#define COFF_DEFAULT_SECTION_ALIGNMENT_POWER (3)
94#define COFF_LONG_FILENAMES
95#define NO_COFF_SYMBOLS
96#define RTYPE2HOWTO(cache_ptr, dst) xcoff_rtype2howto (cache_ptr, dst)
97#define coff_mkobject _bfd_xcoff_mkobject
98#define coff_bfd_copy_private_bfd_data _bfd_xcoff_copy_private_bfd_data
99#define coff_bfd_is_local_label_name _bfd_xcoff_is_local_label_name
100#define coff_bfd_reloc_type_lookup _bfd_xcoff_reloc_type_lookup
101#ifdef AIX_CORE
102extern const bfd_target * rs6000coff_core_p
103  PARAMS ((bfd *abfd));
104extern bfd_boolean rs6000coff_core_file_matches_executable_p
105  PARAMS ((bfd *cbfd, bfd *ebfd));
106extern char *rs6000coff_core_file_failing_command
107  PARAMS ((bfd *abfd));
108extern int rs6000coff_core_file_failing_signal
109  PARAMS ((bfd *abfd));
110#define CORE_FILE_P rs6000coff_core_p
111#define coff_core_file_failing_command \
112  rs6000coff_core_file_failing_command
113#define coff_core_file_failing_signal \
114  rs6000coff_core_file_failing_signal
115#define coff_core_file_matches_executable_p \
116  rs6000coff_core_file_matches_executable_p
117#else
118#define CORE_FILE_P _bfd_dummy_target
119#define coff_core_file_failing_command \
120  _bfd_nocore_core_file_failing_command
121#define coff_core_file_failing_signal \
122  _bfd_nocore_core_file_failing_signal
123#define coff_core_file_matches_executable_p \
124  _bfd_nocore_core_file_matches_executable_p
125#endif
126#define coff_SWAP_sym_in _bfd_xcoff_swap_sym_in
127#define coff_SWAP_sym_out _bfd_xcoff_swap_sym_out
128#define coff_SWAP_aux_in _bfd_xcoff_swap_aux_in
129#define coff_SWAP_aux_out _bfd_xcoff_swap_aux_out
130#define coff_swap_reloc_in xcoff_swap_reloc_in
131#define coff_swap_reloc_out xcoff_swap_reloc_out
132#define NO_COFF_RELOCS
133
134#include "coffcode.h"
135
136/* The main body of code is in coffcode.h.  */
137
138static const char *normalize_filename
139  PARAMS ((bfd *));
140static bfd_boolean xcoff_write_armap_old
141  PARAMS ((bfd *, unsigned int, struct orl *, unsigned int, int));
142static bfd_boolean xcoff_write_armap_big
143  PARAMS ((bfd *, unsigned int, struct orl *, unsigned int, int));
144static bfd_boolean xcoff_write_archive_contents_old
145  PARAMS ((bfd *));
146static bfd_boolean xcoff_write_archive_contents_big
147  PARAMS ((bfd *));
148static void xcoff_swap_ldhdr_in
149  PARAMS ((bfd *, const PTR, struct internal_ldhdr *));
150static void xcoff_swap_ldhdr_out
151  PARAMS ((bfd *, const struct internal_ldhdr *, PTR));
152static void xcoff_swap_ldsym_in
153  PARAMS ((bfd *, const PTR, struct internal_ldsym *));
154static void xcoff_swap_ldsym_out
155  PARAMS ((bfd *, const struct internal_ldsym *, PTR));
156static void xcoff_swap_ldrel_in
157  PARAMS ((bfd *, const PTR, struct internal_ldrel *));
158static void xcoff_swap_ldrel_out
159  PARAMS ((bfd *, const struct internal_ldrel *, PTR));
160static bfd_boolean xcoff_ppc_relocate_section
161  PARAMS ((bfd *, struct bfd_link_info *, bfd *, asection *, bfd_byte *,
162	   struct internal_reloc *, struct internal_syment *, asection **));
163static bfd_boolean _bfd_xcoff_put_ldsymbol_name
164  PARAMS ((bfd *, struct xcoff_loader_info *, struct internal_ldsym *,
165	   const char *));
166static asection *xcoff_create_csect_from_smclas
167  PARAMS ((bfd *, union internal_auxent *, const char *));
168static bfd_boolean xcoff_is_lineno_count_overflow
169  PARAMS ((bfd *, bfd_vma));
170static bfd_boolean xcoff_is_reloc_count_overflow
171  PARAMS ((bfd *, bfd_vma));
172static bfd_vma xcoff_loader_symbol_offset
173  PARAMS ((bfd *, struct internal_ldhdr *));
174static bfd_vma xcoff_loader_reloc_offset
175  PARAMS ((bfd *, struct internal_ldhdr *));
176static bfd_boolean xcoff_generate_rtinit
177  PARAMS ((bfd *, const char *, const char *, bfd_boolean));
178static bfd_boolean do_pad
179  PARAMS ((bfd *, unsigned int));
180static bfd_boolean do_copy
181  PARAMS ((bfd *, bfd *));
182static bfd_boolean do_shared_object_padding
183  PARAMS ((bfd *, bfd *, file_ptr *, int));
184
185/* Relocation functions */
186static bfd_boolean xcoff_reloc_type_br
187  PARAMS ((XCOFF_RELOC_FUNCTION_ARGS));
188
189static bfd_boolean xcoff_complain_overflow_dont_func
190  PARAMS ((XCOFF_COMPLAIN_FUNCTION_ARGS));
191static bfd_boolean xcoff_complain_overflow_bitfield_func
192  PARAMS ((XCOFF_COMPLAIN_FUNCTION_ARGS));
193static bfd_boolean xcoff_complain_overflow_signed_func
194  PARAMS ((XCOFF_COMPLAIN_FUNCTION_ARGS));
195static bfd_boolean xcoff_complain_overflow_unsigned_func
196  PARAMS ((XCOFF_COMPLAIN_FUNCTION_ARGS));
197
198bfd_boolean (*xcoff_calculate_relocation[XCOFF_MAX_CALCULATE_RELOCATION])
199  PARAMS ((XCOFF_RELOC_FUNCTION_ARGS)) =
200{
201  xcoff_reloc_type_pos,	 /* R_POS   (0x00) */
202  xcoff_reloc_type_neg,	 /* R_NEG   (0x01) */
203  xcoff_reloc_type_rel,	 /* R_REL   (0x02) */
204  xcoff_reloc_type_toc,	 /* R_TOC   (0x03) */
205  xcoff_reloc_type_fail, /* R_RTB   (0x04) */
206  xcoff_reloc_type_toc,	 /* R_GL    (0x05) */
207  xcoff_reloc_type_toc,	 /* R_TCL   (0x06) */
208  xcoff_reloc_type_fail, /*	    (0x07) */
209  xcoff_reloc_type_ba,	 /* R_BA    (0x08) */
210  xcoff_reloc_type_fail, /*	    (0x09) */
211  xcoff_reloc_type_br,	 /* R_BR    (0x0a) */
212  xcoff_reloc_type_fail, /*	    (0x0b) */
213  xcoff_reloc_type_pos,	 /* R_RL    (0x0c) */
214  xcoff_reloc_type_pos,	 /* R_RLA   (0x0d) */
215  xcoff_reloc_type_fail, /*	    (0x0e) */
216  xcoff_reloc_type_noop, /* R_REF   (0x0f) */
217  xcoff_reloc_type_fail, /*	    (0x10) */
218  xcoff_reloc_type_fail, /*	    (0x11) */
219  xcoff_reloc_type_toc,	 /* R_TRL   (0x12) */
220  xcoff_reloc_type_toc,	 /* R_TRLA  (0x13) */
221  xcoff_reloc_type_fail, /* R_RRTBI (0x14) */
222  xcoff_reloc_type_fail, /* R_RRTBA (0x15) */
223  xcoff_reloc_type_ba,	 /* R_CAI   (0x16) */
224  xcoff_reloc_type_crel, /* R_CREL  (0x17) */
225  xcoff_reloc_type_ba,	 /* R_RBA   (0x18) */
226  xcoff_reloc_type_ba,	 /* R_RBAC  (0x19) */
227  xcoff_reloc_type_br,	 /* R_RBR   (0x1a) */
228  xcoff_reloc_type_ba,	 /* R_RBRC  (0x1b) */
229};
230
231bfd_boolean (*xcoff_complain_overflow[XCOFF_MAX_COMPLAIN_OVERFLOW])
232  PARAMS ((XCOFF_COMPLAIN_FUNCTION_ARGS)) =
233{
234  xcoff_complain_overflow_dont_func,
235  xcoff_complain_overflow_bitfield_func,
236  xcoff_complain_overflow_signed_func,
237  xcoff_complain_overflow_unsigned_func,
238};
239
240/* We use our own tdata type.  Its first field is the COFF tdata type,
241   so the COFF routines are compatible.  */
242
243bfd_boolean
244_bfd_xcoff_mkobject (abfd)
245     bfd *abfd;
246{
247  coff_data_type *coff;
248  bfd_size_type amt = sizeof (struct xcoff_tdata);
249
250  abfd->tdata.xcoff_obj_data = (struct xcoff_tdata *) bfd_zalloc (abfd, amt);
251  if (abfd->tdata.xcoff_obj_data == NULL)
252    return FALSE;
253  coff = coff_data (abfd);
254  coff->symbols = (coff_symbol_type *) NULL;
255  coff->conversion_table = (unsigned int *) NULL;
256  coff->raw_syments = (struct coff_ptr_struct *) NULL;
257  coff->relocbase = 0;
258
259  xcoff_data (abfd)->modtype = ('1' << 8) | 'L';
260
261  /* We set cputype to -1 to indicate that it has not been
262     initialized.  */
263  xcoff_data (abfd)->cputype = -1;
264
265  xcoff_data (abfd)->csects = NULL;
266  xcoff_data (abfd)->debug_indices = NULL;
267
268  /* text section alignment is different than the default */
269  bfd_xcoff_text_align_power (abfd) = 2;
270
271  return TRUE;
272}
273
274/* Copy XCOFF data from one BFD to another.  */
275
276bfd_boolean
277_bfd_xcoff_copy_private_bfd_data (ibfd, obfd)
278     bfd *ibfd;
279     bfd *obfd;
280{
281  struct xcoff_tdata *ix, *ox;
282  asection *sec;
283
284  if (ibfd->xvec != obfd->xvec)
285    return TRUE;
286  ix = xcoff_data (ibfd);
287  ox = xcoff_data (obfd);
288  ox->full_aouthdr = ix->full_aouthdr;
289  ox->toc = ix->toc;
290  if (ix->sntoc == 0)
291    ox->sntoc = 0;
292  else
293    {
294      sec = coff_section_from_bfd_index (ibfd, ix->sntoc);
295      if (sec == NULL)
296	ox->sntoc = 0;
297      else
298	ox->sntoc = sec->output_section->target_index;
299    }
300  if (ix->snentry == 0)
301    ox->snentry = 0;
302  else
303    {
304      sec = coff_section_from_bfd_index (ibfd, ix->snentry);
305      if (sec == NULL)
306	ox->snentry = 0;
307      else
308	ox->snentry = sec->output_section->target_index;
309    }
310  bfd_xcoff_text_align_power (obfd) = bfd_xcoff_text_align_power (ibfd);
311  bfd_xcoff_data_align_power (obfd) = bfd_xcoff_data_align_power (ibfd);
312  ox->modtype = ix->modtype;
313  ox->cputype = ix->cputype;
314  ox->maxdata = ix->maxdata;
315  ox->maxstack = ix->maxstack;
316  return TRUE;
317}
318
319/* I don't think XCOFF really has a notion of local labels based on
320   name.  This will mean that ld -X doesn't actually strip anything.
321   The AIX native linker does not have a -X option, and it ignores the
322   -x option.  */
323
324bfd_boolean
325_bfd_xcoff_is_local_label_name (abfd, name)
326     bfd *abfd ATTRIBUTE_UNUSED;
327     const char *name ATTRIBUTE_UNUSED;
328{
329  return FALSE;
330}
331
332void
333_bfd_xcoff_swap_sym_in (abfd, ext1, in1)
334     bfd *abfd;
335     PTR ext1;
336     PTR in1;
337{
338  SYMENT *ext = (SYMENT *)ext1;
339  struct internal_syment * in = (struct internal_syment *)in1;
340
341  if (ext->e.e_name[0] != 0)
342    {
343      memcpy (in->_n._n_name, ext->e.e_name, SYMNMLEN);
344    }
345  else
346    {
347      in->_n._n_n._n_zeroes = 0;
348      in->_n._n_n._n_offset = H_GET_32 (abfd, ext->e.e.e_offset);
349    }
350
351  in->n_value = H_GET_32 (abfd, ext->e_value);
352  in->n_scnum = H_GET_16 (abfd, ext->e_scnum);
353  in->n_type = H_GET_16 (abfd, ext->e_type);
354  in->n_sclass = H_GET_8 (abfd, ext->e_sclass);
355  in->n_numaux = H_GET_8 (abfd, ext->e_numaux);
356}
357
358unsigned int
359_bfd_xcoff_swap_sym_out (abfd, inp, extp)
360     bfd *abfd;
361     PTR inp;
362     PTR extp;
363{
364  struct internal_syment *in = (struct internal_syment *)inp;
365  SYMENT *ext =(SYMENT *)extp;
366
367  if (in->_n._n_name[0] != 0)
368    {
369      memcpy (ext->e.e_name, in->_n._n_name, SYMNMLEN);
370    }
371  else
372    {
373      H_PUT_32 (abfd, 0, ext->e.e.e_zeroes);
374      H_PUT_32 (abfd, in->_n._n_n._n_offset, ext->e.e.e_offset);
375    }
376
377  H_PUT_32 (abfd, in->n_value, ext->e_value);
378  H_PUT_16 (abfd, in->n_scnum, ext->e_scnum);
379  H_PUT_16 (abfd, in->n_type, ext->e_type);
380  H_PUT_8 (abfd, in->n_sclass, ext->e_sclass);
381  H_PUT_8 (abfd, in->n_numaux, ext->e_numaux);
382  return bfd_coff_symesz (abfd);
383}
384
385void
386_bfd_xcoff_swap_aux_in (abfd, ext1, type, class, indx, numaux, in1)
387     bfd *abfd;
388     PTR ext1;
389     int type;
390     int class;
391     int indx;
392     int numaux;
393     PTR in1;
394{
395  AUXENT * ext = (AUXENT *)ext1;
396  union internal_auxent *in = (union internal_auxent *)in1;
397
398  switch (class)
399    {
400    case C_FILE:
401      if (ext->x_file.x_fname[0] == 0)
402	{
403	  in->x_file.x_n.x_zeroes = 0;
404	  in->x_file.x_n.x_offset =
405	    H_GET_32 (abfd, ext->x_file.x_n.x_offset);
406	}
407      else
408	{
409	  if (numaux > 1)
410	    {
411	      if (indx == 0)
412		memcpy (in->x_file.x_fname, ext->x_file.x_fname,
413			numaux * sizeof (AUXENT));
414	    }
415	  else
416	    {
417	      memcpy (in->x_file.x_fname, ext->x_file.x_fname, FILNMLEN);
418	    }
419	}
420      goto end;
421
422      /* RS/6000 "csect" auxents */
423    case C_EXT:
424    case C_HIDEXT:
425      if (indx + 1 == numaux)
426	{
427	  in->x_csect.x_scnlen.l = H_GET_32 (abfd, ext->x_csect.x_scnlen);
428	  in->x_csect.x_parmhash = H_GET_32 (abfd, ext->x_csect.x_parmhash);
429	  in->x_csect.x_snhash   = H_GET_16 (abfd, ext->x_csect.x_snhash);
430	  /* We don't have to hack bitfields in x_smtyp because it's
431	     defined by shifts-and-ands, which are equivalent on all
432	     byte orders.  */
433	  in->x_csect.x_smtyp    = H_GET_8 (abfd, ext->x_csect.x_smtyp);
434	  in->x_csect.x_smclas   = H_GET_8 (abfd, ext->x_csect.x_smclas);
435	  in->x_csect.x_stab     = H_GET_32 (abfd, ext->x_csect.x_stab);
436	  in->x_csect.x_snstab   = H_GET_16 (abfd, ext->x_csect.x_snstab);
437	  goto end;
438	}
439      break;
440
441    case C_STAT:
442    case C_LEAFSTAT:
443    case C_HIDDEN:
444      if (type == T_NULL)
445	{
446	  in->x_scn.x_scnlen = H_GET_32 (abfd, ext->x_scn.x_scnlen);
447	  in->x_scn.x_nreloc = H_GET_16 (abfd, ext->x_scn.x_nreloc);
448	  in->x_scn.x_nlinno = H_GET_16 (abfd, ext->x_scn.x_nlinno);
449	  /* PE defines some extra fields; we zero them out for
450	     safety.  */
451	  in->x_scn.x_checksum = 0;
452	  in->x_scn.x_associated = 0;
453	  in->x_scn.x_comdat = 0;
454
455	  goto end;
456	}
457      break;
458    }
459
460  in->x_sym.x_tagndx.l = H_GET_32 (abfd, ext->x_sym.x_tagndx);
461  in->x_sym.x_tvndx = H_GET_16 (abfd, ext->x_sym.x_tvndx);
462
463  if (class == C_BLOCK || class == C_FCN || ISFCN (type) || ISTAG (class))
464    {
465      in->x_sym.x_fcnary.x_fcn.x_lnnoptr =
466	H_GET_32 (abfd, ext->x_sym.x_fcnary.x_fcn.x_lnnoptr);
467      in->x_sym.x_fcnary.x_fcn.x_endndx.l =
468	H_GET_32 (abfd, ext->x_sym.x_fcnary.x_fcn.x_endndx);
469    }
470  else
471    {
472      in->x_sym.x_fcnary.x_ary.x_dimen[0] =
473	H_GET_16 (abfd, ext->x_sym.x_fcnary.x_ary.x_dimen[0]);
474      in->x_sym.x_fcnary.x_ary.x_dimen[1] =
475	H_GET_16 (abfd, ext->x_sym.x_fcnary.x_ary.x_dimen[1]);
476      in->x_sym.x_fcnary.x_ary.x_dimen[2] =
477	H_GET_16 (abfd, ext->x_sym.x_fcnary.x_ary.x_dimen[2]);
478      in->x_sym.x_fcnary.x_ary.x_dimen[3] =
479	H_GET_16 (abfd, ext->x_sym.x_fcnary.x_ary.x_dimen[3]);
480    }
481
482  if (ISFCN (type))
483    {
484      in->x_sym.x_misc.x_fsize = H_GET_32 (abfd, ext->x_sym.x_misc.x_fsize);
485    }
486  else
487    {
488      in->x_sym.x_misc.x_lnsz.x_lnno =
489	H_GET_16 (abfd, ext->x_sym.x_misc.x_lnsz.x_lnno);
490      in->x_sym.x_misc.x_lnsz.x_size =
491	H_GET_16 (abfd, ext->x_sym.x_misc.x_lnsz.x_size);
492    }
493
494 end: ;
495  /* The semicolon is because MSVC doesn't like labels at
496     end of block.  */
497}
498
499
500unsigned int _bfd_xcoff_swap_aux_out
501  PARAMS ((bfd *, PTR, int, int, int, int, PTR));
502
503unsigned int
504_bfd_xcoff_swap_aux_out (abfd, inp, type, class, indx, numaux, extp)
505     bfd * abfd;
506     PTR   inp;
507     int   type;
508     int   class;
509     int   indx ATTRIBUTE_UNUSED;
510     int   numaux ATTRIBUTE_UNUSED;
511     PTR   extp;
512{
513  union internal_auxent *in = (union internal_auxent *)inp;
514  AUXENT *ext = (AUXENT *)extp;
515
516  memset ((PTR)ext, 0, bfd_coff_auxesz (abfd));
517  switch (class)
518    {
519    case C_FILE:
520      if (in->x_file.x_fname[0] == 0)
521	{
522	  H_PUT_32 (abfd, 0, ext->x_file.x_n.x_zeroes);
523	  H_PUT_32 (abfd, in->x_file.x_n.x_offset, ext->x_file.x_n.x_offset);
524	}
525      else
526	{
527	  memcpy (ext->x_file.x_fname, in->x_file.x_fname, FILNMLEN);
528	}
529      goto end;
530
531      /* RS/6000 "csect" auxents */
532    case C_EXT:
533    case C_HIDEXT:
534      if (indx + 1 == numaux)
535	{
536	  H_PUT_32 (abfd, in->x_csect.x_scnlen.l, ext->x_csect.x_scnlen);
537	  H_PUT_32 (abfd, in->x_csect.x_parmhash, ext->x_csect.x_parmhash);
538	  H_PUT_16 (abfd, in->x_csect.x_snhash, ext->x_csect.x_snhash);
539	  /* We don't have to hack bitfields in x_smtyp because it's
540	     defined by shifts-and-ands, which are equivalent on all
541	     byte orders.  */
542	  H_PUT_8 (abfd, in->x_csect.x_smtyp, ext->x_csect.x_smtyp);
543	  H_PUT_8 (abfd, in->x_csect.x_smclas, ext->x_csect.x_smclas);
544	  H_PUT_32 (abfd, in->x_csect.x_stab, ext->x_csect.x_stab);
545	  H_PUT_16 (abfd, in->x_csect.x_snstab, ext->x_csect.x_snstab);
546	  goto end;
547	}
548      break;
549
550    case C_STAT:
551    case C_LEAFSTAT:
552    case C_HIDDEN:
553      if (type == T_NULL)
554	{
555	  H_PUT_32 (abfd, in->x_scn.x_scnlen, ext->x_scn.x_scnlen);
556	  H_PUT_16 (abfd, in->x_scn.x_nreloc, ext->x_scn.x_nreloc);
557	  H_PUT_16 (abfd, in->x_scn.x_nlinno, ext->x_scn.x_nlinno);
558	  goto end;
559	}
560      break;
561    }
562
563  H_PUT_32 (abfd, in->x_sym.x_tagndx.l, ext->x_sym.x_tagndx);
564  H_PUT_16 (abfd, in->x_sym.x_tvndx, ext->x_sym.x_tvndx);
565
566  if (class == C_BLOCK || class == C_FCN || ISFCN (type) || ISTAG (class))
567    {
568      H_PUT_32 (abfd, in->x_sym.x_fcnary.x_fcn.x_lnnoptr,
569		ext->x_sym.x_fcnary.x_fcn.x_lnnoptr);
570      H_PUT_32 (abfd, in->x_sym.x_fcnary.x_fcn.x_endndx.l,
571		ext->x_sym.x_fcnary.x_fcn.x_endndx);
572    }
573  else
574    {
575      H_PUT_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[0],
576		ext->x_sym.x_fcnary.x_ary.x_dimen[0]);
577      H_PUT_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[1],
578		ext->x_sym.x_fcnary.x_ary.x_dimen[1]);
579      H_PUT_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[2],
580		ext->x_sym.x_fcnary.x_ary.x_dimen[2]);
581      H_PUT_16 (abfd, in->x_sym.x_fcnary.x_ary.x_dimen[3],
582		ext->x_sym.x_fcnary.x_ary.x_dimen[3]);
583    }
584
585  if (ISFCN (type))
586    H_PUT_32 (abfd, in->x_sym.x_misc.x_fsize, ext->x_sym.x_misc.x_fsize);
587  else
588    {
589      H_PUT_16 (abfd, in->x_sym.x_misc.x_lnsz.x_lnno,
590		ext->x_sym.x_misc.x_lnsz.x_lnno);
591      H_PUT_16 (abfd, in->x_sym.x_misc.x_lnsz.x_size,
592		ext->x_sym.x_misc.x_lnsz.x_size);
593    }
594
595end:
596  return bfd_coff_auxesz (abfd);
597}
598
599
600
601/* The XCOFF reloc table.  Actually, XCOFF relocations specify the
602   bitsize and whether they are signed or not, along with a
603   conventional type.  This table is for the types, which are used for
604   different algorithms for putting in the reloc.  Many of these
605   relocs need special_function entries, which I have not written.  */
606
607
608reloc_howto_type xcoff_howto_table[] =
609{
610  /* Standard 32 bit relocation.  */
611  HOWTO (R_POS,			/* type */
612	 0,			/* rightshift */
613	 2,			/* size (0 = byte, 1 = short, 2 = long) */
614	 32,			/* bitsize */
615	 FALSE,			/* pc_relative */
616	 0,			/* bitpos */
617	 complain_overflow_bitfield, /* complain_on_overflow */
618	 0,			/* special_function */
619	 "R_POS",		/* name */
620	 TRUE,			/* partial_inplace */
621	 0xffffffff,		/* src_mask */
622	 0xffffffff,		/* dst_mask */
623	 FALSE),		/* pcrel_offset */
624
625  /* 32 bit relocation, but store negative value.  */
626  HOWTO (R_NEG,			/* type */
627	 0,			/* rightshift */
628	 -2,			/* size (0 = byte, 1 = short, 2 = long) */
629	 32,			/* bitsize */
630	 FALSE,			/* pc_relative */
631	 0,			/* bitpos */
632	 complain_overflow_bitfield, /* complain_on_overflow */
633	 0,			/* special_function */
634	 "R_NEG",		/* name */
635	 TRUE,			/* partial_inplace */
636	 0xffffffff,		/* src_mask */
637	 0xffffffff,		/* dst_mask */
638	 FALSE),		/* pcrel_offset */
639
640  /* 32 bit PC relative relocation.  */
641  HOWTO (R_REL,			/* type */
642	 0,			/* rightshift */
643	 2,			/* size (0 = byte, 1 = short, 2 = long) */
644	 32,			/* bitsize */
645	 TRUE,			/* pc_relative */
646	 0,			/* bitpos */
647	 complain_overflow_signed, /* complain_on_overflow */
648	 0,			/* special_function */
649	 "R_REL",		/* name */
650	 TRUE,			/* partial_inplace */
651	 0xffffffff,		/* src_mask */
652	 0xffffffff,		/* dst_mask */
653	 FALSE),		/* pcrel_offset */
654
655  /* 16 bit TOC relative relocation.  */
656  HOWTO (R_TOC,			/* type */
657	 0,			/* rightshift */
658	 1,			/* size (0 = byte, 1 = short, 2 = long) */
659	 16,			/* bitsize */
660	 FALSE,			/* pc_relative */
661	 0,			/* bitpos */
662	 complain_overflow_bitfield, /* complain_on_overflow */
663	 0,			/* special_function */
664	 "R_TOC",		/* name */
665	 TRUE,			/* partial_inplace */
666	 0xffff,		/* src_mask */
667	 0xffff,		/* dst_mask */
668	 FALSE),		/* pcrel_offset */
669
670  /* I don't really know what this is.  */
671  HOWTO (R_RTB,			/* type */
672	 1,			/* rightshift */
673	 2,			/* size (0 = byte, 1 = short, 2 = long) */
674	 32,			/* bitsize */
675	 FALSE,			/* pc_relative */
676	 0,			/* bitpos */
677	 complain_overflow_bitfield, /* complain_on_overflow */
678	 0,			/* special_function */
679	 "R_RTB",		/* name */
680	 TRUE,			/* partial_inplace */
681	 0xffffffff,		/* src_mask */
682	 0xffffffff,		/* dst_mask */
683	 FALSE),		/* pcrel_offset */
684
685  /* External TOC relative symbol.  */
686  HOWTO (R_GL,			/* type */
687	 0,			/* rightshift */
688	 1,			/* size (0 = byte, 1 = short, 2 = long) */
689	 16,			/* bitsize */
690	 FALSE,			/* pc_relative */
691	 0,			/* bitpos */
692	 complain_overflow_bitfield, /* complain_on_overflow */
693	 0,			/* special_function */
694	 "R_GL",		/* name */
695	 TRUE,			/* partial_inplace */
696	 0xffff,		/* src_mask */
697	 0xffff,		/* dst_mask */
698	 FALSE),		/* pcrel_offset */
699
700  /* Local TOC relative symbol.	 */
701  HOWTO (R_TCL,			/* type */
702	 0,			/* rightshift */
703	 1,			/* size (0 = byte, 1 = short, 2 = long) */
704	 16,			/* bitsize */
705	 FALSE,			/* pc_relative */
706	 0,			/* bitpos */
707	 complain_overflow_bitfield, /* complain_on_overflow */
708	 0,			/* special_function */
709	 "R_TCL",		/* name */
710	 TRUE,			/* partial_inplace */
711	 0xffff,		/* src_mask */
712	 0xffff,		/* dst_mask */
713	 FALSE),		/* pcrel_offset */
714
715  EMPTY_HOWTO (7),
716
717  /* Non modifiable absolute branch.  */
718  HOWTO (R_BA,			/* type */
719	 0,			/* rightshift */
720	 2,			/* size (0 = byte, 1 = short, 2 = long) */
721	 26,			/* bitsize */
722	 FALSE,			/* pc_relative */
723	 0,			/* bitpos */
724	 complain_overflow_bitfield, /* complain_on_overflow */
725	 0,			/* special_function */
726	 "R_BA_26",		/* name */
727	 TRUE,			/* partial_inplace */
728	 0x03fffffc,		/* src_mask */
729	 0x03fffffc,		/* dst_mask */
730	 FALSE),		/* pcrel_offset */
731
732  EMPTY_HOWTO (9),
733
734  /* Non modifiable relative branch.  */
735  HOWTO (R_BR,			/* type */
736	 0,			/* rightshift */
737	 2,			/* size (0 = byte, 1 = short, 2 = long) */
738	 26,			/* bitsize */
739	 TRUE,			/* pc_relative */
740	 0,			/* bitpos */
741	 complain_overflow_signed, /* complain_on_overflow */
742	 0,			/* special_function */
743	 "R_BR",		/* name */
744	 TRUE,			/* partial_inplace */
745	 0x03fffffc,		/* src_mask */
746	 0x03fffffc,		/* dst_mask */
747	 FALSE),		/* pcrel_offset */
748
749  EMPTY_HOWTO (0xb),
750
751  /* Indirect load.  */
752  HOWTO (R_RL,			/* type */
753	 0,			/* rightshift */
754	 1,			/* size (0 = byte, 1 = short, 2 = long) */
755	 16,			/* bitsize */
756	 FALSE,			/* pc_relative */
757	 0,			/* bitpos */
758	 complain_overflow_bitfield, /* complain_on_overflow */
759	 0,			/* special_function */
760	 "R_RL",		/* name */
761	 TRUE,			/* partial_inplace */
762	 0xffff,		/* src_mask */
763	 0xffff,		/* dst_mask */
764	 FALSE),		/* pcrel_offset */
765
766  /* Load address.  */
767  HOWTO (R_RLA,			/* type */
768	 0,			/* rightshift */
769	 1,			/* size (0 = byte, 1 = short, 2 = long) */
770	 16,			/* bitsize */
771	 FALSE,			/* pc_relative */
772	 0,			/* bitpos */
773	 complain_overflow_bitfield, /* complain_on_overflow */
774	 0,			/* special_function */
775	 "R_RLA",		/* name */
776	 TRUE,			/* partial_inplace */
777	 0xffff,		/* src_mask */
778	 0xffff,		/* dst_mask */
779	 FALSE),		/* pcrel_offset */
780
781  EMPTY_HOWTO (0xe),
782
783  /* Non-relocating reference.  */
784  HOWTO (R_REF,			/* type */
785	 0,			/* rightshift */
786	 2,			/* size (0 = byte, 1 = short, 2 = long) */
787	 32,			/* bitsize */
788	 FALSE,			/* pc_relative */
789	 0,			/* bitpos */
790	 complain_overflow_dont, /* complain_on_overflow */
791	 0,			/* special_function */
792	 "R_REF",		/* name */
793	 FALSE,			/* partial_inplace */
794	 0,			/* src_mask */
795	 0,			/* dst_mask */
796	 FALSE),		/* pcrel_offset */
797
798  EMPTY_HOWTO (0x10),
799  EMPTY_HOWTO (0x11),
800
801  /* TOC relative indirect load.  */
802  HOWTO (R_TRL,			/* type */
803	 0,			/* rightshift */
804	 1,			/* size (0 = byte, 1 = short, 2 = long) */
805	 16,			/* bitsize */
806	 FALSE,			/* pc_relative */
807	 0,			/* bitpos */
808	 complain_overflow_bitfield, /* complain_on_overflow */
809	 0,			/* special_function */
810	 "R_TRL",		/* name */
811	 TRUE,			/* partial_inplace */
812	 0xffff,		/* src_mask */
813	 0xffff,		/* dst_mask */
814	 FALSE),		/* pcrel_offset */
815
816  /* TOC relative load address.  */
817  HOWTO (R_TRLA,		/* type */
818	 0,			/* rightshift */
819	 1,			/* size (0 = byte, 1 = short, 2 = long) */
820	 16,			/* bitsize */
821	 FALSE,			/* pc_relative */
822	 0,			/* bitpos */
823	 complain_overflow_bitfield, /* complain_on_overflow */
824	 0,			/* special_function */
825	 "R_TRLA",		/* name */
826	 TRUE,			/* partial_inplace */
827	 0xffff,		/* src_mask */
828	 0xffff,		/* dst_mask */
829	 FALSE),		/* pcrel_offset */
830
831  /* Modifiable relative branch.  */
832  HOWTO (R_RRTBI,		 /* type */
833	 1,			/* rightshift */
834	 2,			/* size (0 = byte, 1 = short, 2 = long) */
835	 32,			/* bitsize */
836	 FALSE,			/* pc_relative */
837	 0,			/* bitpos */
838	 complain_overflow_bitfield, /* complain_on_overflow */
839	 0,			/* special_function */
840	 "R_RRTBI",		/* name */
841	 TRUE,			/* partial_inplace */
842	 0xffffffff,		/* src_mask */
843	 0xffffffff,		/* dst_mask */
844	 FALSE),		/* pcrel_offset */
845
846  /* Modifiable absolute branch.  */
847  HOWTO (R_RRTBA,		 /* type */
848	 1,			/* rightshift */
849	 2,			/* size (0 = byte, 1 = short, 2 = long) */
850	 32,			/* bitsize */
851	 FALSE,			/* pc_relative */
852	 0,			/* bitpos */
853	 complain_overflow_bitfield, /* complain_on_overflow */
854	 0,			/* special_function */
855	 "R_RRTBA",		/* name */
856	 TRUE,			/* partial_inplace */
857	 0xffffffff,		/* src_mask */
858	 0xffffffff,		/* dst_mask */
859	 FALSE),		/* pcrel_offset */
860
861  /* Modifiable call absolute indirect.  */
862  HOWTO (R_CAI,			/* type */
863	 0,			/* rightshift */
864	 1,			/* size (0 = byte, 1 = short, 2 = long) */
865	 16,			/* bitsize */
866	 FALSE,			/* pc_relative */
867	 0,			/* bitpos */
868	 complain_overflow_bitfield, /* complain_on_overflow */
869	 0,			/* special_function */
870	 "R_CAI",		/* name */
871	 TRUE,			/* partial_inplace */
872	 0xffff,		/* src_mask */
873	 0xffff,		/* dst_mask */
874	 FALSE),		/* pcrel_offset */
875
876  /* Modifiable call relative.  */
877  HOWTO (R_CREL,		/* type */
878	 0,			/* rightshift */
879	 1,			/* size (0 = byte, 1 = short, 2 = long) */
880	 16,			/* bitsize */
881	 FALSE,			/* pc_relative */
882	 0,			/* bitpos */
883	 complain_overflow_bitfield, /* complain_on_overflow */
884	 0,			/* special_function */
885	 "R_CREL",		/* name */
886	 TRUE,			/* partial_inplace */
887	 0xffff,		/* src_mask */
888	 0xffff,		/* dst_mask */
889	 FALSE),		/* pcrel_offset */
890
891  /* Modifiable branch absolute.  */
892  HOWTO (R_RBA,			/* type */
893	 0,			/* rightshift */
894	 2,			/* size (0 = byte, 1 = short, 2 = long) */
895	 26,			/* bitsize */
896	 FALSE,			/* pc_relative */
897	 0,			/* bitpos */
898	 complain_overflow_bitfield, /* complain_on_overflow */
899	 0,			/* special_function */
900	 "R_RBA",		/* name */
901	 TRUE,			/* partial_inplace */
902	 0x03fffffc,		/* src_mask */
903	 0x03fffffc,		/* dst_mask */
904	 FALSE),		/* pcrel_offset */
905
906  /* Modifiable branch absolute.  */
907  HOWTO (R_RBAC,		/* type */
908	 0,			/* rightshift */
909	 2,			/* size (0 = byte, 1 = short, 2 = long) */
910	 32,			/* bitsize */
911	 FALSE,			/* pc_relative */
912	 0,			/* bitpos */
913	 complain_overflow_bitfield, /* complain_on_overflow */
914	 0,			/* special_function */
915	 "R_RBAC",		/* name */
916	 TRUE,			/* partial_inplace */
917	 0xffffffff,		/* src_mask */
918	 0xffffffff,		/* dst_mask */
919	 FALSE),		/* pcrel_offset */
920
921  /* Modifiable branch relative.  */
922  HOWTO (R_RBR,			/* type */
923	 0,			/* rightshift */
924	 2,			/* size (0 = byte, 1 = short, 2 = long) */
925	 26,			/* bitsize */
926	 FALSE,			/* pc_relative */
927	 0,			/* bitpos */
928	 complain_overflow_signed, /* complain_on_overflow */
929	 0,			/* special_function */
930	 "R_RBR_26",		/* name */
931	 TRUE,			/* partial_inplace */
932	 0x03fffffc,		/* src_mask */
933	 0x03fffffc,		/* dst_mask */
934	 FALSE),		/* pcrel_offset */
935
936  /* Modifiable branch absolute.  */
937  HOWTO (R_RBRC,		/* type */
938	 0,			/* rightshift */
939	 1,			/* size (0 = byte, 1 = short, 2 = long) */
940	 16,			/* bitsize */
941	 FALSE,			/* pc_relative */
942	 0,			/* bitpos */
943	 complain_overflow_bitfield, /* complain_on_overflow */
944	 0,			/* special_function */
945	 "R_RBRC",		/* name */
946	 TRUE,			/* partial_inplace */
947	 0xffff,		/* src_mask */
948	 0xffff,		/* dst_mask */
949	 FALSE),		/* pcrel_offset */
950
951  /* 16 bit Non modifiable absolute branch.  */
952  HOWTO (R_BA,			/* type */
953	 0,			/* rightshift */
954	 1,			/* size (0 = byte, 1 = short, 2 = long) */
955	 16,			/* bitsize */
956	 FALSE,			/* pc_relative */
957	 0,			/* bitpos */
958	 complain_overflow_bitfield, /* complain_on_overflow */
959	 0,			/* special_function */
960	 "R_BA_16",		/* name */
961	 TRUE,			/* partial_inplace */
962	 0xfffc,		/* src_mask */
963	 0xfffc,		/* dst_mask */
964	 FALSE),		/* pcrel_offset */
965
966  /* Modifiable branch relative.  */
967  HOWTO (R_RBR,			/* type */
968	 0,			/* rightshift */
969	 1,			/* size (0 = byte, 1 = short, 2 = long) */
970	 16,			/* bitsize */
971	 FALSE,			/* pc_relative */
972	 0,			/* bitpos */
973	 complain_overflow_signed, /* complain_on_overflow */
974	 0,			/* special_function */
975	 "R_RBR_16",		/* name */
976	 TRUE,			/* partial_inplace */
977	 0xffff,		/* src_mask */
978	 0xffff,		/* dst_mask */
979	 FALSE),		/* pcrel_offset */
980
981  /* Modifiable branch relative.  */
982  HOWTO (R_RBA,			/* type */
983	 0,			/* rightshift */
984	 1,			/* size (0 = byte, 1 = short, 2 = long) */
985	 16,			/* bitsize */
986	 FALSE,			/* pc_relative */
987	 0,			/* bitpos */
988	 complain_overflow_signed, /* complain_on_overflow */
989	 0,			/* special_function */
990	 "R_RBA_16",		/* name */
991	 TRUE,			/* partial_inplace */
992	 0xffff,		/* src_mask */
993	 0xffff,		/* dst_mask */
994	 FALSE),		/* pcrel_offset */
995
996};
997
998void
999xcoff_rtype2howto (relent, internal)
1000     arelent *relent;
1001     struct internal_reloc *internal;
1002{
1003  if (internal->r_type > R_RBRC)
1004    abort ();
1005
1006  /* Default howto layout works most of the time */
1007  relent->howto = &xcoff_howto_table[internal->r_type];
1008
1009  /* Special case some 16 bit reloc */
1010  if (15 == (internal->r_size & 0x1f))
1011    {
1012      if (R_BA == internal->r_type)
1013	relent->howto = &xcoff_howto_table[0x1c];
1014      else if (R_RBR == internal->r_type)
1015	relent->howto = &xcoff_howto_table[0x1d];
1016      else if (R_RBA == internal->r_type)
1017	relent->howto = &xcoff_howto_table[0x1e];
1018    }
1019
1020  /* The r_size field of an XCOFF reloc encodes the bitsize of the
1021     relocation, as well as indicating whether it is signed or not.
1022     Doublecheck that the relocation information gathered from the
1023     type matches this information.  The bitsize is not significant
1024     for R_REF relocs.  */
1025  if (relent->howto->dst_mask != 0
1026      && (relent->howto->bitsize
1027	  != ((unsigned int) internal->r_size & 0x1f) + 1))
1028    abort ();
1029}
1030
1031reloc_howto_type *
1032_bfd_xcoff_reloc_type_lookup (abfd, code)
1033     bfd *abfd ATTRIBUTE_UNUSED;
1034     bfd_reloc_code_real_type code;
1035{
1036  switch (code)
1037    {
1038    case BFD_RELOC_PPC_B26:
1039      return &xcoff_howto_table[0xa];
1040    case BFD_RELOC_PPC_BA16:
1041      return &xcoff_howto_table[0x1c];
1042    case BFD_RELOC_PPC_BA26:
1043      return &xcoff_howto_table[8];
1044    case BFD_RELOC_PPC_TOC16:
1045      return &xcoff_howto_table[3];
1046    case BFD_RELOC_32:
1047    case BFD_RELOC_CTOR:
1048      return &xcoff_howto_table[0];
1049    default:
1050      return NULL;
1051    }
1052}
1053
1054
1055/* XCOFF archive support.  The original version of this code was by
1056   Damon A. Permezel.  It was enhanced to permit cross support, and
1057   writing archive files, by Ian Lance Taylor, Cygnus Support.
1058
1059   XCOFF uses its own archive format.  Everything is hooked together
1060   with file offset links, so it is possible to rapidly update an
1061   archive in place.  Of course, we don't do that.  An XCOFF archive
1062   has a real file header, not just an ARMAG string.  The structure of
1063   the file header and of each archive header appear below.
1064
1065   An XCOFF archive also has a member table, which is a list of
1066   elements in the archive (you can get that by looking through the
1067   linked list, but you have to read a lot more of the file).  The
1068   member table has a normal archive header with an empty name.  It is
1069   normally (and perhaps must be) the second to last entry in the
1070   archive.  The member table data is almost printable ASCII.  It
1071   starts with a 12 character decimal string which is the number of
1072   entries in the table.  For each entry it has a 12 character decimal
1073   string which is the offset in the archive of that member.  These
1074   entries are followed by a series of null terminated strings which
1075   are the member names for each entry.
1076
1077   Finally, an XCOFF archive has a global symbol table, which is what
1078   we call the armap.  The global symbol table has a normal archive
1079   header with an empty name.  It is normally (and perhaps must be)
1080   the last entry in the archive.  The contents start with a four byte
1081   binary number which is the number of entries.  This is followed by
1082   a that many four byte binary numbers; each is the file offset of an
1083   entry in the archive.  These numbers are followed by a series of
1084   null terminated strings, which are symbol names.
1085
1086   AIX 4.3 introduced a new archive format which can handle larger
1087   files and also 32- and 64-bit objects in the same archive.  The
1088   things said above remain true except that there is now more than
1089   one global symbol table.  The one is used to index 32-bit objects,
1090   the other for 64-bit objects.
1091
1092   The new archives (recognizable by the new ARMAG string) has larger
1093   field lengths so that we cannot really share any code.  Also we have
1094   to take care that we are not generating the new form of archives
1095   on AIX 4.2 or earlier systems.  */
1096
1097/* XCOFF archives use this as a magic string.  Note that both strings
1098   have the same length.  */
1099
1100/* Set the magic for archive.  */
1101
1102bfd_boolean
1103bfd_xcoff_ar_archive_set_magic (abfd, magic)
1104     bfd *abfd ATTRIBUTE_UNUSED;
1105     char *magic ATTRIBUTE_UNUSED;
1106{
1107  /* Not supported yet.  */
1108  return FALSE;
1109 /* bfd_xcoff_archive_set_magic (abfd, magic); */
1110}
1111
1112/* Read in the armap of an XCOFF archive.  */
1113
1114bfd_boolean
1115_bfd_xcoff_slurp_armap (abfd)
1116     bfd *abfd;
1117{
1118  file_ptr off;
1119  size_t namlen;
1120  bfd_size_type sz;
1121  bfd_byte *contents, *cend;
1122  bfd_vma c, i;
1123  carsym *arsym;
1124  bfd_byte *p;
1125
1126  if (xcoff_ardata (abfd) == NULL)
1127    {
1128      bfd_has_map (abfd) = FALSE;
1129      return TRUE;
1130    }
1131
1132  if (! xcoff_big_format_p (abfd))
1133    {
1134      /* This is for the old format.  */
1135      struct xcoff_ar_hdr hdr;
1136
1137      off = strtol (xcoff_ardata (abfd)->symoff, (char **) NULL, 10);
1138      if (off == 0)
1139	{
1140	  bfd_has_map (abfd) = FALSE;
1141	  return TRUE;
1142	}
1143
1144      if (bfd_seek (abfd, off, SEEK_SET) != 0)
1145	return FALSE;
1146
1147      /* The symbol table starts with a normal archive header.  */
1148      if (bfd_bread ((PTR) &hdr, (bfd_size_type) SIZEOF_AR_HDR, abfd)
1149	  != SIZEOF_AR_HDR)
1150	return FALSE;
1151
1152      /* Skip the name (normally empty).  */
1153      namlen = strtol (hdr.namlen, (char **) NULL, 10);
1154      off = ((namlen + 1) & ~ (size_t) 1) + SXCOFFARFMAG;
1155      if (bfd_seek (abfd, off, SEEK_CUR) != 0)
1156	return FALSE;
1157
1158      sz = strtol (hdr.size, (char **) NULL, 10);
1159
1160      /* Read in the entire symbol table.  */
1161      contents = (bfd_byte *) bfd_alloc (abfd, sz);
1162      if (contents == NULL)
1163	return FALSE;
1164      if (bfd_bread ((PTR) contents, sz, abfd) != sz)
1165	return FALSE;
1166
1167      /* The symbol table starts with a four byte count.  */
1168      c = H_GET_32 (abfd, contents);
1169
1170      if (c * 4 >= sz)
1171	{
1172	  bfd_set_error (bfd_error_bad_value);
1173	  return FALSE;
1174	}
1175
1176      bfd_ardata (abfd)->symdefs =
1177	((carsym *) bfd_alloc (abfd, c * sizeof (carsym)));
1178      if (bfd_ardata (abfd)->symdefs == NULL)
1179	return FALSE;
1180
1181      /* After the count comes a list of four byte file offsets.  */
1182      for (i = 0, arsym = bfd_ardata (abfd)->symdefs, p = contents + 4;
1183	   i < c;
1184	   ++i, ++arsym, p += 4)
1185	arsym->file_offset = H_GET_32 (abfd, p);
1186    }
1187  else
1188    {
1189      /* This is for the new format.  */
1190      struct xcoff_ar_hdr_big hdr;
1191
1192      off = strtol (xcoff_ardata_big (abfd)->symoff, (char **) NULL, 10);
1193      if (off == 0)
1194	{
1195	  bfd_has_map (abfd) = FALSE;
1196	  return TRUE;
1197	}
1198
1199      if (bfd_seek (abfd, off, SEEK_SET) != 0)
1200	return FALSE;
1201
1202      /* The symbol table starts with a normal archive header.  */
1203      if (bfd_bread ((PTR) &hdr, (bfd_size_type) SIZEOF_AR_HDR_BIG, abfd)
1204	  != SIZEOF_AR_HDR_BIG)
1205	return FALSE;
1206
1207      /* Skip the name (normally empty).  */
1208      namlen = strtol (hdr.namlen, (char **) NULL, 10);
1209      off = ((namlen + 1) & ~ (size_t) 1) + SXCOFFARFMAG;
1210      if (bfd_seek (abfd, off, SEEK_CUR) != 0)
1211	return FALSE;
1212
1213      /* XXX This actually has to be a call to strtoll (at least on 32-bit
1214	 machines) since the field width is 20 and there numbers with more
1215	 than 32 bits can be represented.  */
1216      sz = strtol (hdr.size, (char **) NULL, 10);
1217
1218      /* Read in the entire symbol table.  */
1219      contents = (bfd_byte *) bfd_alloc (abfd, sz);
1220      if (contents == NULL)
1221	return FALSE;
1222      if (bfd_bread ((PTR) contents, sz, abfd) != sz)
1223	return FALSE;
1224
1225      /* The symbol table starts with an eight byte count.  */
1226      c = H_GET_64 (abfd, contents);
1227
1228      if (c * 8 >= sz)
1229	{
1230	  bfd_set_error (bfd_error_bad_value);
1231	  return FALSE;
1232	}
1233
1234      bfd_ardata (abfd)->symdefs =
1235	((carsym *) bfd_alloc (abfd, c * sizeof (carsym)));
1236      if (bfd_ardata (abfd)->symdefs == NULL)
1237	return FALSE;
1238
1239      /* After the count comes a list of eight byte file offsets.  */
1240      for (i = 0, arsym = bfd_ardata (abfd)->symdefs, p = contents + 8;
1241	   i < c;
1242	   ++i, ++arsym, p += 8)
1243	arsym->file_offset = H_GET_64 (abfd, p);
1244    }
1245
1246  /* After the file offsets come null terminated symbol names.  */
1247  cend = contents + sz;
1248  for (i = 0, arsym = bfd_ardata (abfd)->symdefs;
1249       i < c;
1250       ++i, ++arsym, p += strlen ((char *) p) + 1)
1251    {
1252      if (p >= cend)
1253	{
1254	  bfd_set_error (bfd_error_bad_value);
1255	  return FALSE;
1256	}
1257      arsym->name = (char *) p;
1258    }
1259
1260  bfd_ardata (abfd)->symdef_count = c;
1261  bfd_has_map (abfd) = TRUE;
1262
1263  return TRUE;
1264}
1265
1266/* See if this is an XCOFF archive.  */
1267
1268const bfd_target *
1269_bfd_xcoff_archive_p (abfd)
1270     bfd *abfd;
1271{
1272  struct artdata *tdata_hold;
1273  char magic[SXCOFFARMAG];
1274  bfd_size_type amt = SXCOFFARMAG;
1275
1276  if (bfd_bread ((PTR) magic, amt, abfd) != amt)
1277    {
1278      if (bfd_get_error () != bfd_error_system_call)
1279	bfd_set_error (bfd_error_wrong_format);
1280      return NULL;
1281    }
1282
1283  if (strncmp (magic, XCOFFARMAG, SXCOFFARMAG) != 0
1284      && strncmp (magic, XCOFFARMAGBIG, SXCOFFARMAG) != 0)
1285    {
1286      bfd_set_error (bfd_error_wrong_format);
1287      return NULL;
1288    }
1289
1290  tdata_hold = bfd_ardata (abfd);
1291
1292  amt = sizeof (struct artdata);
1293  bfd_ardata (abfd) = (struct artdata *) bfd_zalloc (abfd, amt);
1294  if (bfd_ardata (abfd) == (struct artdata *) NULL)
1295    goto error_ret_restore;
1296
1297  bfd_ardata (abfd)->cache = NULL;
1298  bfd_ardata (abfd)->archive_head = NULL;
1299  bfd_ardata (abfd)->symdefs = NULL;
1300  bfd_ardata (abfd)->extended_names = NULL;
1301
1302  /* Now handle the two formats.  */
1303  if (magic[1] != 'b')
1304    {
1305      /* This is the old format.  */
1306      struct xcoff_ar_file_hdr hdr;
1307
1308      /* Copy over the magic string.  */
1309      memcpy (hdr.magic, magic, SXCOFFARMAG);
1310
1311      /* Now read the rest of the file header.  */
1312      amt = SIZEOF_AR_FILE_HDR - SXCOFFARMAG;
1313      if (bfd_bread ((PTR) &hdr.memoff, amt, abfd) != amt)
1314	{
1315	  if (bfd_get_error () != bfd_error_system_call)
1316	    bfd_set_error (bfd_error_wrong_format);
1317	  goto error_ret;
1318	}
1319
1320      bfd_ardata (abfd)->first_file_filepos = strtol (hdr.firstmemoff,
1321						      (char **) NULL, 10);
1322
1323      amt = SIZEOF_AR_FILE_HDR;
1324      bfd_ardata (abfd)->tdata = bfd_zalloc (abfd, amt);
1325      if (bfd_ardata (abfd)->tdata == NULL)
1326	goto error_ret;
1327
1328      memcpy (bfd_ardata (abfd)->tdata, &hdr, SIZEOF_AR_FILE_HDR);
1329    }
1330  else
1331    {
1332      /* This is the new format.  */
1333      struct xcoff_ar_file_hdr_big hdr;
1334
1335      /* Copy over the magic string.  */
1336      memcpy (hdr.magic, magic, SXCOFFARMAG);
1337
1338      /* Now read the rest of the file header.  */
1339      amt = SIZEOF_AR_FILE_HDR_BIG - SXCOFFARMAG;
1340      if (bfd_bread ((PTR) &hdr.memoff, amt, abfd) != amt)
1341	{
1342	  if (bfd_get_error () != bfd_error_system_call)
1343	    bfd_set_error (bfd_error_wrong_format);
1344	  goto error_ret;
1345	}
1346
1347      bfd_ardata (abfd)->first_file_filepos = bfd_scan_vma (hdr.firstmemoff,
1348							    (const char **) 0,
1349							    10);
1350
1351      amt = SIZEOF_AR_FILE_HDR_BIG;
1352      bfd_ardata (abfd)->tdata = bfd_zalloc (abfd, amt);
1353      if (bfd_ardata (abfd)->tdata == NULL)
1354	goto error_ret;
1355
1356      memcpy (bfd_ardata (abfd)->tdata, &hdr, SIZEOF_AR_FILE_HDR_BIG);
1357    }
1358
1359  if (! _bfd_xcoff_slurp_armap (abfd))
1360    {
1361    error_ret:
1362      bfd_release (abfd, bfd_ardata (abfd));
1363    error_ret_restore:
1364      bfd_ardata (abfd) = tdata_hold;
1365      return NULL;
1366    }
1367
1368  return abfd->xvec;
1369}
1370
1371/* Read the archive header in an XCOFF archive.  */
1372
1373PTR
1374_bfd_xcoff_read_ar_hdr (abfd)
1375     bfd *abfd;
1376{
1377  bfd_size_type namlen;
1378  struct areltdata *ret;
1379  bfd_size_type amt = sizeof (struct areltdata);
1380
1381  ret = (struct areltdata *) bfd_alloc (abfd, amt);
1382  if (ret == NULL)
1383    return NULL;
1384
1385  if (! xcoff_big_format_p (abfd))
1386    {
1387      struct xcoff_ar_hdr hdr;
1388      struct xcoff_ar_hdr *hdrp;
1389
1390      if (bfd_bread ((PTR) &hdr, (bfd_size_type) SIZEOF_AR_HDR, abfd)
1391	  != SIZEOF_AR_HDR)
1392	{
1393	  free (ret);
1394	  return NULL;
1395	}
1396
1397      namlen = strtol (hdr.namlen, (char **) NULL, 10);
1398      amt = SIZEOF_AR_HDR + namlen + 1;
1399      hdrp = (struct xcoff_ar_hdr *) bfd_alloc (abfd, amt);
1400      if (hdrp == NULL)
1401	{
1402	  free (ret);
1403	  return NULL;
1404	}
1405      memcpy (hdrp, &hdr, SIZEOF_AR_HDR);
1406      if (bfd_bread ((char *) hdrp + SIZEOF_AR_HDR, namlen, abfd) != namlen)
1407	{
1408	  free (ret);
1409	  return NULL;
1410	}
1411      ((char *) hdrp)[SIZEOF_AR_HDR + namlen] = '\0';
1412
1413      ret->arch_header = (char *) hdrp;
1414      ret->parsed_size = strtol (hdr.size, (char **) NULL, 10);
1415      ret->filename = (char *) hdrp + SIZEOF_AR_HDR;
1416    }
1417  else
1418    {
1419      struct xcoff_ar_hdr_big hdr;
1420      struct xcoff_ar_hdr_big *hdrp;
1421
1422      if (bfd_bread ((PTR) &hdr, (bfd_size_type) SIZEOF_AR_HDR_BIG, abfd)
1423	  != SIZEOF_AR_HDR_BIG)
1424	{
1425	  free (ret);
1426	  return NULL;
1427	}
1428
1429      namlen = strtol (hdr.namlen, (char **) NULL, 10);
1430      amt = SIZEOF_AR_HDR_BIG + namlen + 1;
1431      hdrp = (struct xcoff_ar_hdr_big *) bfd_alloc (abfd, amt);
1432      if (hdrp == NULL)
1433	{
1434	  free (ret);
1435	  return NULL;
1436	}
1437      memcpy (hdrp, &hdr, SIZEOF_AR_HDR_BIG);
1438      if (bfd_bread ((char *) hdrp + SIZEOF_AR_HDR_BIG, namlen, abfd) != namlen)
1439	{
1440	  free (ret);
1441	  return NULL;
1442	}
1443      ((char *) hdrp)[SIZEOF_AR_HDR_BIG + namlen] = '\0';
1444
1445      ret->arch_header = (char *) hdrp;
1446      /* XXX This actually has to be a call to strtoll (at least on 32-bit
1447	 machines) since the field width is 20 and there numbers with more
1448	 than 32 bits can be represented.  */
1449      ret->parsed_size = strtol (hdr.size, (char **) NULL, 10);
1450      ret->filename = (char *) hdrp + SIZEOF_AR_HDR_BIG;
1451    }
1452
1453  /* Skip over the XCOFFARFMAG at the end of the file name.  */
1454  if (bfd_seek (abfd, (file_ptr) ((namlen & 1) + SXCOFFARFMAG), SEEK_CUR) != 0)
1455    return NULL;
1456
1457  return (PTR) ret;
1458}
1459
1460/* Open the next element in an XCOFF archive.  */
1461
1462bfd *
1463_bfd_xcoff_openr_next_archived_file (archive, last_file)
1464     bfd *archive;
1465     bfd *last_file;
1466{
1467  file_ptr filestart;
1468
1469  if (xcoff_ardata (archive) == NULL)
1470    {
1471      bfd_set_error (bfd_error_invalid_operation);
1472      return NULL;
1473    }
1474
1475  if (! xcoff_big_format_p (archive))
1476    {
1477      if (last_file == NULL)
1478	filestart = bfd_ardata (archive)->first_file_filepos;
1479      else
1480	filestart = strtol (arch_xhdr (last_file)->nextoff, (char **) NULL,
1481			    10);
1482
1483      if (filestart == 0
1484	  || filestart == strtol (xcoff_ardata (archive)->memoff,
1485				  (char **) NULL, 10)
1486	  || filestart == strtol (xcoff_ardata (archive)->symoff,
1487				  (char **) NULL, 10))
1488	{
1489	  bfd_set_error (bfd_error_no_more_archived_files);
1490	  return NULL;
1491	}
1492    }
1493  else
1494    {
1495      if (last_file == NULL)
1496	filestart = bfd_ardata (archive)->first_file_filepos;
1497      else
1498	/* XXX These actually have to be a calls to strtoll (at least
1499	   on 32-bit machines) since the fields's width is 20 and
1500	   there numbers with more than 32 bits can be represented.  */
1501	filestart = strtol (arch_xhdr_big (last_file)->nextoff, (char **) NULL,
1502			    10);
1503
1504      /* XXX These actually have to be calls to strtoll (at least on 32-bit
1505	 machines) since the fields's width is 20 and there numbers with more
1506	 than 32 bits can be represented.  */
1507      if (filestart == 0
1508	  || filestart == strtol (xcoff_ardata_big (archive)->memoff,
1509				  (char **) NULL, 10)
1510	  || filestart == strtol (xcoff_ardata_big (archive)->symoff,
1511				  (char **) NULL, 10))
1512	{
1513	  bfd_set_error (bfd_error_no_more_archived_files);
1514	  return NULL;
1515	}
1516    }
1517
1518  return _bfd_get_elt_at_filepos (archive, filestart);
1519}
1520
1521/* Stat an element in an XCOFF archive.  */
1522
1523int
1524_bfd_xcoff_stat_arch_elt (abfd, s)
1525     bfd *abfd;
1526     struct stat *s;
1527{
1528  if (abfd->arelt_data == NULL)
1529    {
1530      bfd_set_error (bfd_error_invalid_operation);
1531      return -1;
1532    }
1533
1534  if (! xcoff_big_format_p (abfd->my_archive))
1535    {
1536      struct xcoff_ar_hdr *hdrp = arch_xhdr (abfd);
1537
1538      s->st_mtime = strtol (hdrp->date, (char **) NULL, 10);
1539      s->st_uid = strtol (hdrp->uid, (char **) NULL, 10);
1540      s->st_gid = strtol (hdrp->gid, (char **) NULL, 10);
1541      s->st_mode = strtol (hdrp->mode, (char **) NULL, 8);
1542      s->st_size = arch_eltdata (abfd)->parsed_size;
1543    }
1544  else
1545    {
1546      struct xcoff_ar_hdr_big *hdrp = arch_xhdr_big (abfd);
1547
1548      s->st_mtime = strtol (hdrp->date, (char **) NULL, 10);
1549      s->st_uid = strtol (hdrp->uid, (char **) NULL, 10);
1550      s->st_gid = strtol (hdrp->gid, (char **) NULL, 10);
1551      s->st_mode = strtol (hdrp->mode, (char **) NULL, 8);
1552      s->st_size = arch_eltdata (abfd)->parsed_size;
1553    }
1554
1555  return 0;
1556}
1557
1558/* Normalize a file name for inclusion in an archive.  */
1559
1560static const char *
1561normalize_filename (abfd)
1562     bfd *abfd;
1563{
1564  const char *file;
1565  const char *filename;
1566
1567  file = bfd_get_filename (abfd);
1568  filename = strrchr (file, '/');
1569  if (filename != NULL)
1570    filename++;
1571  else
1572    filename = file;
1573  return filename;
1574}
1575
1576/* Write out an XCOFF armap.  */
1577
1578static bfd_boolean
1579xcoff_write_armap_old (abfd, elength, map, orl_count, stridx)
1580     bfd *abfd;
1581     unsigned int elength ATTRIBUTE_UNUSED;
1582     struct orl *map;
1583     unsigned int orl_count;
1584     int stridx;
1585{
1586  struct xcoff_ar_hdr hdr;
1587  char *p;
1588  unsigned char buf[4];
1589  bfd *sub;
1590  file_ptr fileoff;
1591  unsigned int i;
1592
1593  memset (&hdr, 0, sizeof hdr);
1594  sprintf (hdr.size, "%ld", (long) (4 + orl_count * 4 + stridx));
1595  sprintf (hdr.nextoff, "%d", 0);
1596  memcpy (hdr.prevoff, xcoff_ardata (abfd)->memoff, XCOFFARMAG_ELEMENT_SIZE);
1597  sprintf (hdr.date, "%d", 0);
1598  sprintf (hdr.uid, "%d", 0);
1599  sprintf (hdr.gid, "%d", 0);
1600  sprintf (hdr.mode, "%d", 0);
1601  sprintf (hdr.namlen, "%d", 0);
1602
1603  /* We need spaces, not null bytes, in the header.  */
1604  for (p = (char *) &hdr; p < (char *) &hdr + SIZEOF_AR_HDR; p++)
1605    if (*p == '\0')
1606      *p = ' ';
1607
1608  if (bfd_bwrite ((PTR) &hdr, (bfd_size_type) SIZEOF_AR_HDR, abfd)
1609      != SIZEOF_AR_HDR
1610      || (bfd_bwrite (XCOFFARFMAG, (bfd_size_type) SXCOFFARFMAG, abfd)
1611	  != SXCOFFARFMAG))
1612    return FALSE;
1613
1614  H_PUT_32 (abfd, orl_count, buf);
1615  if (bfd_bwrite (buf, (bfd_size_type) 4, abfd) != 4)
1616    return FALSE;
1617
1618  sub = abfd->archive_head;
1619  fileoff = SIZEOF_AR_FILE_HDR;
1620  i = 0;
1621  while (sub != NULL && i < orl_count)
1622    {
1623      size_t namlen;
1624
1625      while (map[i].u.abfd == sub)
1626	{
1627	  H_PUT_32 (abfd, fileoff, buf);
1628	  if (bfd_bwrite (buf, (bfd_size_type) 4, abfd) != 4)
1629	    return FALSE;
1630	  ++i;
1631	}
1632      namlen = strlen (normalize_filename (sub));
1633      namlen = (namlen + 1) &~ (size_t) 1;
1634      fileoff += (SIZEOF_AR_HDR
1635		  + namlen
1636		  + SXCOFFARFMAG
1637		  + arelt_size (sub));
1638      fileoff = (fileoff + 1) &~ 1;
1639      sub = sub->next;
1640    }
1641
1642  for (i = 0; i < orl_count; i++)
1643    {
1644      const char *name;
1645      size_t namlen;
1646
1647      name = *map[i].name;
1648      namlen = strlen (name);
1649      if (bfd_bwrite (name, (bfd_size_type) (namlen + 1), abfd) != namlen + 1)
1650	return FALSE;
1651    }
1652
1653  if ((stridx & 1) != 0)
1654    {
1655      char b;
1656
1657      b = '\0';
1658      if (bfd_bwrite (&b, (bfd_size_type) 1, abfd) != 1)
1659	return FALSE;
1660    }
1661
1662  return TRUE;
1663}
1664
1665static char buff20[XCOFFARMAGBIG_ELEMENT_SIZE + 1];
1666#define FMT20  "%-20lld"
1667#define FMT12  "%-12d"
1668#define FMT12_OCTAL  "%-12o"
1669#define FMT4  "%-4d"
1670#define PRINT20(d, v) \
1671  sprintf (buff20, FMT20, (long long)(v)), \
1672  memcpy ((void *) (d), buff20, 20)
1673
1674#define PRINT12(d, v) \
1675  sprintf (buff20, FMT12, (int)(v)), \
1676  memcpy ((void *) (d), buff20, 12)
1677
1678#define PRINT12_OCTAL(d, v) \
1679  sprintf (buff20, FMT12_OCTAL, (unsigned int)(v)), \
1680  memcpy ((void *) (d), buff20, 12)
1681
1682#define PRINT4(d, v) \
1683  sprintf (buff20, FMT4, (int)(v)), \
1684  memcpy ((void *) (d), buff20, 4)
1685
1686#define READ20(d, v) \
1687  buff20[20] = 0, \
1688  memcpy (buff20, (d), 20), \
1689  (v) = bfd_scan_vma (buff20, (const char **) NULL, 10)
1690
1691static bfd_boolean
1692do_pad (abfd, number)
1693     bfd *abfd;
1694     unsigned int number;
1695{
1696  bfd_byte b = 0;
1697
1698  /* Limit pad to <= 4096.  */
1699  if (number > 4096)
1700    return FALSE;
1701
1702  while (number--)
1703    if (bfd_bwrite (&b, (bfd_size_type) 1, abfd) != 1)
1704      return FALSE;
1705
1706  return TRUE;
1707}
1708
1709static bfd_boolean
1710do_copy (out_bfd, in_bfd)
1711     bfd *out_bfd;
1712     bfd *in_bfd;
1713{
1714  bfd_size_type remaining;
1715  bfd_byte buffer[DEFAULT_BUFFERSIZE];
1716
1717  if (bfd_seek (in_bfd, (file_ptr) 0, SEEK_SET) != 0)
1718    return FALSE;
1719
1720  remaining = arelt_size (in_bfd);
1721
1722  while (remaining >= DEFAULT_BUFFERSIZE)
1723    {
1724      if (bfd_bread (buffer, DEFAULT_BUFFERSIZE, in_bfd) != DEFAULT_BUFFERSIZE
1725	  || bfd_bwrite (buffer, DEFAULT_BUFFERSIZE, out_bfd) != DEFAULT_BUFFERSIZE)
1726	return FALSE;
1727
1728      remaining -= DEFAULT_BUFFERSIZE;
1729    }
1730
1731  if (remaining)
1732    {
1733      if (bfd_bread (buffer, remaining, in_bfd) != remaining
1734	  || bfd_bwrite (buffer, remaining, out_bfd) != remaining)
1735	return FALSE;
1736    }
1737
1738  return TRUE;
1739}
1740
1741static bfd_boolean
1742do_shared_object_padding (out_bfd, in_bfd, offset, ar_header_size)
1743     bfd *out_bfd;
1744     bfd *in_bfd;
1745     file_ptr *offset;
1746     int ar_header_size;
1747{
1748  if (bfd_check_format (in_bfd, bfd_object)
1749      && bfd_get_flavour (in_bfd) == bfd_target_xcoff_flavour
1750      && (in_bfd->flags & DYNAMIC) != 0)
1751    {
1752      bfd_size_type pad = 0;
1753      int text_align_power;
1754
1755      text_align_power = bfd_xcoff_text_align_power (in_bfd);
1756
1757      pad = 1 << text_align_power;
1758      pad -= (*offset + ar_header_size) & (pad - 1);
1759
1760      if (! do_pad (out_bfd, pad))
1761	return FALSE;
1762
1763      *offset += pad;
1764    }
1765
1766  return TRUE;
1767}
1768
1769static bfd_boolean
1770xcoff_write_armap_big (abfd, elength, map, orl_count, stridx)
1771     bfd *abfd;
1772     unsigned int elength ATTRIBUTE_UNUSED;
1773     struct orl *map;
1774     unsigned int orl_count;
1775     int stridx;
1776{
1777  struct xcoff_ar_file_hdr_big *fhdr;
1778  bfd_vma i, sym_32, sym_64, str_32, str_64;
1779  const bfd_arch_info_type *arch_info = NULL;
1780  bfd *current_bfd;
1781  size_t string_length;
1782  file_ptr nextoff, prevoff;
1783
1784  /* First, we look through the symbols and work out which are
1785     from 32-bit objects and which from 64-bit ones.  */
1786  sym_32 = sym_64 = str_32 = str_64 = 0;
1787
1788  current_bfd = abfd->archive_head;
1789  if (current_bfd != NULL)
1790    arch_info = bfd_get_arch_info (current_bfd);
1791    i = 0;
1792    while (current_bfd != NULL && i < orl_count)
1793    {
1794      while (map[i].u.abfd == current_bfd)
1795	{
1796	  string_length = strlen (*map[i].name) + 1;
1797
1798	  if (arch_info->bits_per_address == 64)
1799	    {
1800	      sym_64++;
1801	      str_64 += string_length;
1802	    }
1803	  else
1804	    {
1805	      sym_32++;
1806	      str_32 += string_length;
1807	    }
1808	  i++;
1809	}
1810      current_bfd = current_bfd->next;
1811      if (current_bfd != NULL)
1812	arch_info = bfd_get_arch_info (current_bfd);
1813    }
1814
1815  /* A quick sanity check... */
1816  BFD_ASSERT (sym_64 + sym_32 == orl_count);
1817  /* Explicit cast to int for compiler.  */
1818  BFD_ASSERT ((int)(str_64 + str_32) == stridx);
1819
1820  fhdr = xcoff_ardata_big (abfd);
1821
1822  /* xcoff_write_archive_contents_big passes nextoff in symoff. */
1823  READ20 (fhdr->memoff, prevoff);
1824  READ20 (fhdr->symoff, nextoff);
1825
1826  BFD_ASSERT (nextoff == bfd_tell (abfd));
1827
1828  /* Write out the symbol table.
1829     Layout :
1830
1831     standard big archive header
1832     0x0000		      ar_size	[0x14]
1833     0x0014		      ar_nxtmem [0x14]
1834     0x0028		      ar_prvmem [0x14]
1835     0x003C		      ar_date	[0x0C]
1836     0x0048		      ar_uid	[0x0C]
1837     0x0054		      ar_gid	[0x0C]
1838     0x0060		      ar_mod	[0x0C]
1839     0x006C		      ar_namelen[0x04]
1840     0x0070		      ar_fmag	[SXCOFFARFMAG]
1841
1842     Symbol table
1843     0x0072		      num_syms	[0x08], binary
1844     0x0078		      offsets	[0x08 * num_syms], binary
1845     0x0086 + 0x08 * num_syms names	[??]
1846     ??			      pad to even bytes.
1847  */
1848
1849  if (sym_32)
1850    {
1851      struct xcoff_ar_hdr_big *hdr;
1852      bfd_byte *symbol_table;
1853      bfd_byte *st;
1854      file_ptr fileoff;
1855
1856      bfd_vma symbol_table_size =
1857	SIZEOF_AR_HDR_BIG
1858	+ SXCOFFARFMAG
1859	+ 8
1860	+ 8 * sym_32
1861	+ str_32 + (str_32 & 1);
1862
1863      symbol_table = NULL;
1864      symbol_table = (bfd_byte *) bfd_zmalloc (symbol_table_size);
1865      if (symbol_table == NULL)
1866	return FALSE;
1867
1868      hdr = (struct xcoff_ar_hdr_big *) symbol_table;
1869
1870      PRINT20 (hdr->size, 8 + 8 * sym_32 + str_32 + (str_32 & 1));
1871
1872      if (sym_64)
1873	PRINT20 (hdr->nextoff, nextoff + symbol_table_size);
1874      else
1875	PRINT20 (hdr->nextoff, 0);
1876
1877      PRINT20 (hdr->prevoff, prevoff);
1878      PRINT12 (hdr->date, 0);
1879      PRINT12 (hdr->uid, 0);
1880      PRINT12 (hdr->gid, 0);
1881      PRINT12 (hdr->mode, 0);
1882      PRINT4 (hdr->namlen, 0) ;
1883
1884      st = symbol_table + SIZEOF_AR_HDR_BIG;
1885      memcpy (st, XCOFFARFMAG, SXCOFFARFMAG);
1886      st += SXCOFFARFMAG;
1887
1888      bfd_h_put_64 (abfd, sym_32, st);
1889      st += 8;
1890
1891      /* loop over the 32 bit offsets */
1892      current_bfd = abfd->archive_head;
1893      if (current_bfd != NULL)
1894	arch_info = bfd_get_arch_info (current_bfd);
1895      fileoff = SIZEOF_AR_FILE_HDR_BIG;
1896      i = 0;
1897      while (current_bfd != NULL && i < orl_count)
1898	{
1899	  while (map[i].u.abfd == current_bfd)
1900	    {
1901	      if (arch_info->bits_per_address == 32)
1902		{
1903		  bfd_h_put_64 (abfd, fileoff, st);
1904		  st += 8;
1905		}
1906	      i++;
1907	    }
1908	  string_length = strlen (normalize_filename (current_bfd));
1909	  string_length += string_length & 1;
1910	  fileoff += (SIZEOF_AR_HDR_BIG
1911		      + string_length
1912		      + SXCOFFARFMAG
1913		      + arelt_size (current_bfd));
1914	  fileoff += fileoff & 1;
1915	  current_bfd = current_bfd->next;
1916	  if (current_bfd != NULL)
1917	    arch_info = bfd_get_arch_info (current_bfd);
1918	}
1919
1920      /* loop over the 32 bit symbol names */
1921      current_bfd = abfd->archive_head;
1922      if (current_bfd != NULL)
1923	arch_info = bfd_get_arch_info (current_bfd);
1924      i = 0;
1925      while (current_bfd != NULL && i < orl_count)
1926	{
1927	  while (map[i].u.abfd == current_bfd)
1928	    {
1929	      if (arch_info->bits_per_address == 32)
1930		{
1931		  string_length = sprintf (st, "%s", *map[i].name);
1932		  st += string_length + 1;
1933		}
1934	      i++;
1935	    }
1936	  current_bfd = current_bfd->next;
1937	  if (current_bfd != NULL)
1938	    arch_info = bfd_get_arch_info (current_bfd);
1939	}
1940
1941      bfd_bwrite (symbol_table, symbol_table_size, abfd);
1942
1943      free (symbol_table);
1944      symbol_table = NULL;
1945
1946      prevoff = nextoff;
1947      nextoff = nextoff + symbol_table_size;
1948    }
1949  else
1950    PRINT20 (fhdr->symoff, 0);
1951
1952  if (sym_64)
1953    {
1954      struct xcoff_ar_hdr_big *hdr;
1955      bfd_byte *symbol_table;
1956      bfd_byte *st;
1957      file_ptr fileoff;
1958
1959      bfd_vma symbol_table_size =
1960	SIZEOF_AR_HDR_BIG
1961	+ SXCOFFARFMAG
1962	+ 8
1963	+ 8 * sym_64
1964	+ str_64 + (str_64 & 1);
1965
1966      symbol_table = NULL;
1967      symbol_table = (bfd_byte *) bfd_zmalloc (symbol_table_size);
1968      if (symbol_table == NULL)
1969	return FALSE;
1970
1971      hdr = (struct xcoff_ar_hdr_big *) symbol_table;
1972
1973      PRINT20 (hdr->size, 8 + 8 * sym_64 + str_64 + (str_64 & 1));
1974      PRINT20 (hdr->nextoff, 0);
1975      PRINT20 (hdr->prevoff, prevoff);
1976      PRINT12 (hdr->date, 0);
1977      PRINT12 (hdr->uid, 0);
1978      PRINT12 (hdr->gid, 0);
1979      PRINT12 (hdr->mode, 0);
1980      PRINT4 (hdr->namlen, 0);
1981
1982      st = symbol_table + SIZEOF_AR_HDR_BIG;
1983      memcpy (st, XCOFFARFMAG, SXCOFFARFMAG);
1984      st += SXCOFFARFMAG;
1985
1986      bfd_h_put_64 (abfd, sym_64, st);
1987      st += 8;
1988
1989      /* loop over the 64 bit offsets */
1990      current_bfd = abfd->archive_head;
1991      if (current_bfd != NULL)
1992	arch_info = bfd_get_arch_info (current_bfd);
1993      fileoff = SIZEOF_AR_FILE_HDR_BIG;
1994      i = 0;
1995      while (current_bfd != NULL && i < orl_count)
1996	{
1997	  while (map[i].u.abfd == current_bfd)
1998	    {
1999	      if (arch_info->bits_per_address == 64)
2000		{
2001		  bfd_h_put_64 (abfd, fileoff, st);
2002		  st += 8;
2003		}
2004	      i++;
2005	    }
2006	  string_length = strlen (normalize_filename (current_bfd));
2007	  string_length += string_length & 1;
2008	  fileoff += (SIZEOF_AR_HDR_BIG
2009		      + string_length
2010		      + SXCOFFARFMAG
2011		      + arelt_size (current_bfd));
2012	  fileoff += fileoff & 1;
2013	  current_bfd = current_bfd->next;
2014	  if (current_bfd != NULL)
2015	    arch_info = bfd_get_arch_info (current_bfd);
2016	}
2017
2018      /* loop over the 64 bit symbol names */
2019      current_bfd = abfd->archive_head;
2020      if (current_bfd != NULL)
2021	arch_info = bfd_get_arch_info (current_bfd);
2022      i = 0;
2023      while (current_bfd != NULL && i < orl_count)
2024	{
2025	  while (map[i].u.abfd == current_bfd)
2026	    {
2027	      if (arch_info->bits_per_address == 64)
2028		{
2029		  string_length = sprintf (st, "%s", *map[i].name);
2030		  st += string_length + 1;
2031		}
2032	      i++;
2033	    }
2034	  current_bfd = current_bfd->next;
2035	  if (current_bfd != NULL)
2036	    arch_info = bfd_get_arch_info (current_bfd);
2037	}
2038
2039      bfd_bwrite (symbol_table, symbol_table_size, abfd);
2040
2041      free (symbol_table);
2042      symbol_table = NULL;
2043
2044      PRINT20 (fhdr->symoff64, nextoff);
2045    }
2046  else
2047    PRINT20 (fhdr->symoff64, 0);
2048
2049  return TRUE;
2050}
2051
2052bfd_boolean
2053_bfd_xcoff_write_armap (abfd, elength, map, orl_count, stridx)
2054     bfd *abfd;
2055     unsigned int elength ATTRIBUTE_UNUSED;
2056     struct orl *map;
2057     unsigned int orl_count;
2058     int stridx;
2059{
2060  if (! xcoff_big_format_p (abfd))
2061    return xcoff_write_armap_old (abfd, elength, map, orl_count, stridx);
2062  else
2063    return xcoff_write_armap_big (abfd, elength, map, orl_count, stridx);
2064}
2065
2066/* Write out an XCOFF archive.  We always write an entire archive,
2067   rather than fussing with the freelist and so forth.  */
2068
2069static bfd_boolean
2070xcoff_write_archive_contents_old (abfd)
2071     bfd *abfd;
2072{
2073  struct xcoff_ar_file_hdr fhdr;
2074  bfd_size_type count;
2075  bfd_size_type total_namlen;
2076  file_ptr *offsets;
2077  bfd_boolean makemap;
2078  bfd_boolean hasobjects;
2079  file_ptr prevoff, nextoff;
2080  bfd *sub;
2081  size_t i;
2082  struct xcoff_ar_hdr ahdr;
2083  bfd_size_type size;
2084  char *p;
2085  char decbuf[XCOFFARMAG_ELEMENT_SIZE + 1];
2086
2087  memset (&fhdr, 0, sizeof fhdr);
2088  strncpy (fhdr.magic, XCOFFARMAG, SXCOFFARMAG);
2089  sprintf (fhdr.firstmemoff, "%d", SIZEOF_AR_FILE_HDR);
2090  sprintf (fhdr.freeoff, "%d", 0);
2091
2092  count = 0;
2093  total_namlen = 0;
2094  for (sub = abfd->archive_head; sub != NULL; sub = sub->next)
2095    {
2096      ++count;
2097      total_namlen += strlen (normalize_filename (sub)) + 1;
2098    }
2099  offsets = (file_ptr *) bfd_alloc (abfd, count * sizeof (file_ptr));
2100  if (offsets == NULL)
2101    return FALSE;
2102
2103  if (bfd_seek (abfd, (file_ptr) SIZEOF_AR_FILE_HDR, SEEK_SET) != 0)
2104    return FALSE;
2105
2106  makemap = bfd_has_map (abfd);
2107  hasobjects = FALSE;
2108  prevoff = 0;
2109  nextoff = SIZEOF_AR_FILE_HDR;
2110  for (sub = abfd->archive_head, i = 0; sub != NULL; sub = sub->next, i++)
2111    {
2112      const char *name;
2113      bfd_size_type namlen;
2114      struct xcoff_ar_hdr *ahdrp;
2115      bfd_size_type remaining;
2116
2117      if (makemap && ! hasobjects)
2118	{
2119	  if (bfd_check_format (sub, bfd_object))
2120	    hasobjects = TRUE;
2121	}
2122
2123      name = normalize_filename (sub);
2124      namlen = strlen (name);
2125
2126      if (sub->arelt_data != NULL)
2127	ahdrp = arch_xhdr (sub);
2128      else
2129	ahdrp = NULL;
2130
2131      if (ahdrp == NULL)
2132	{
2133	  struct stat s;
2134
2135	  memset (&ahdr, 0, sizeof ahdr);
2136	  ahdrp = &ahdr;
2137	  if (stat (bfd_get_filename (sub), &s) != 0)
2138	    {
2139	      bfd_set_error (bfd_error_system_call);
2140	      return FALSE;
2141	    }
2142
2143	  sprintf (ahdrp->size, "%ld", (long) s.st_size);
2144	  sprintf (ahdrp->date, "%ld", (long) s.st_mtime);
2145	  sprintf (ahdrp->uid, "%ld", (long) s.st_uid);
2146	  sprintf (ahdrp->gid, "%ld", (long) s.st_gid);
2147	  sprintf (ahdrp->mode, "%o", (unsigned int) s.st_mode);
2148
2149	  if (sub->arelt_data == NULL)
2150	    {
2151	      size = sizeof (struct areltdata);
2152	      sub->arelt_data = bfd_alloc (sub, size);
2153	      if (sub->arelt_data == NULL)
2154		return FALSE;
2155	    }
2156
2157	  arch_eltdata (sub)->parsed_size = s.st_size;
2158	}
2159
2160      sprintf (ahdrp->prevoff, "%ld", (long) prevoff);
2161      sprintf (ahdrp->namlen, "%ld", (long) namlen);
2162
2163      /* If the length of the name is odd, we write out the null byte
2164	 after the name as well.  */
2165      namlen = (namlen + 1) &~ (bfd_size_type) 1;
2166
2167      remaining = arelt_size (sub);
2168      size = (SIZEOF_AR_HDR
2169	      + namlen
2170	      + SXCOFFARFMAG
2171	      + remaining);
2172
2173      BFD_ASSERT (nextoff == bfd_tell (abfd));
2174
2175      offsets[i] = nextoff;
2176
2177      prevoff = nextoff;
2178      nextoff += size + (size & 1);
2179
2180      sprintf (ahdrp->nextoff, "%ld", (long) nextoff);
2181
2182      /* We need spaces, not null bytes, in the header.  */
2183      for (p = (char *) ahdrp; p < (char *) ahdrp + SIZEOF_AR_HDR; p++)
2184	if (*p == '\0')
2185	  *p = ' ';
2186
2187      if ((bfd_bwrite ((PTR) ahdrp, (bfd_size_type) SIZEOF_AR_HDR, abfd)
2188	   != SIZEOF_AR_HDR)
2189	  || bfd_bwrite ((PTR) name, namlen, abfd) != namlen
2190	  || bfd_bwrite ((PTR) XCOFFARFMAG, (bfd_size_type) SXCOFFARFMAG,
2191			 abfd) != SXCOFFARFMAG)
2192	return FALSE;
2193
2194      if (bfd_seek (sub, (file_ptr) 0, SEEK_SET) != 0)
2195	return FALSE;
2196
2197      if (! do_copy (abfd, sub))
2198	return FALSE;
2199
2200      if (! do_pad (abfd, size & 1))
2201	return FALSE;
2202    }
2203
2204  sprintf (fhdr.lastmemoff, "%ld", (long) prevoff);
2205
2206  /* Write out the member table.  */
2207
2208  BFD_ASSERT (nextoff == bfd_tell (abfd));
2209  sprintf (fhdr.memoff, "%ld", (long) nextoff);
2210
2211  memset (&ahdr, 0, sizeof ahdr);
2212  sprintf (ahdr.size, "%ld", (long) (XCOFFARMAG_ELEMENT_SIZE
2213				     + count * XCOFFARMAG_ELEMENT_SIZE
2214				     + total_namlen));
2215  sprintf (ahdr.prevoff, "%ld", (long) prevoff);
2216  sprintf (ahdr.date, "%d", 0);
2217  sprintf (ahdr.uid, "%d", 0);
2218  sprintf (ahdr.gid, "%d", 0);
2219  sprintf (ahdr.mode, "%d", 0);
2220  sprintf (ahdr.namlen, "%d", 0);
2221
2222  size = (SIZEOF_AR_HDR
2223	  + XCOFFARMAG_ELEMENT_SIZE
2224	  + count * XCOFFARMAG_ELEMENT_SIZE
2225	  + total_namlen
2226	  + SXCOFFARFMAG);
2227
2228  prevoff = nextoff;
2229  nextoff += size + (size & 1);
2230
2231  if (makemap && hasobjects)
2232    sprintf (ahdr.nextoff, "%ld", (long) nextoff);
2233  else
2234    sprintf (ahdr.nextoff, "%d", 0);
2235
2236  /* We need spaces, not null bytes, in the header.  */
2237  for (p = (char *) &ahdr; p < (char *) &ahdr + SIZEOF_AR_HDR; p++)
2238    if (*p == '\0')
2239      *p = ' ';
2240
2241  if ((bfd_bwrite ((PTR) &ahdr, (bfd_size_type) SIZEOF_AR_HDR, abfd)
2242       != SIZEOF_AR_HDR)
2243      || (bfd_bwrite ((PTR) XCOFFARFMAG, (bfd_size_type) SXCOFFARFMAG, abfd)
2244	  != SXCOFFARFMAG))
2245    return FALSE;
2246
2247  sprintf (decbuf, "%-12ld", (long) count);
2248  if (bfd_bwrite ((PTR) decbuf, (bfd_size_type) XCOFFARMAG_ELEMENT_SIZE, abfd)
2249      != XCOFFARMAG_ELEMENT_SIZE)
2250    return FALSE;
2251  for (i = 0; i < (size_t) count; i++)
2252    {
2253      sprintf (decbuf, "%-12ld", (long) offsets[i]);
2254      if (bfd_bwrite ((PTR) decbuf, (bfd_size_type) XCOFFARMAG_ELEMENT_SIZE,
2255		      abfd) != XCOFFARMAG_ELEMENT_SIZE)
2256	return FALSE;
2257    }
2258  for (sub = abfd->archive_head; sub != NULL; sub = sub->next)
2259    {
2260      const char *name;
2261      bfd_size_type namlen;
2262
2263      name = normalize_filename (sub);
2264      namlen = strlen (name);
2265      if (bfd_bwrite ((PTR) name, namlen + 1, abfd) != namlen + 1)
2266	return FALSE;
2267    }
2268
2269  if (! do_pad (abfd, size & 1))
2270    return FALSE;
2271
2272  /* Write out the armap, if appropriate.  */
2273  if (! makemap || ! hasobjects)
2274    sprintf (fhdr.symoff, "%d", 0);
2275  else
2276    {
2277      BFD_ASSERT (nextoff == bfd_tell (abfd));
2278      sprintf (fhdr.symoff, "%ld", (long) nextoff);
2279      bfd_ardata (abfd)->tdata = (PTR) &fhdr;
2280      if (! _bfd_compute_and_write_armap (abfd, 0))
2281	return FALSE;
2282    }
2283
2284  /* Write out the archive file header.  */
2285
2286  /* We need spaces, not null bytes, in the header.  */
2287  for (p = (char *) &fhdr; p < (char *) &fhdr + SIZEOF_AR_FILE_HDR; p++)
2288    if (*p == '\0')
2289      *p = ' ';
2290
2291  if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0
2292      || (bfd_bwrite ((PTR) &fhdr, (bfd_size_type) SIZEOF_AR_FILE_HDR, abfd)
2293	  != SIZEOF_AR_FILE_HDR))
2294    return FALSE;
2295
2296  return TRUE;
2297}
2298
2299static bfd_boolean
2300xcoff_write_archive_contents_big (abfd)
2301     bfd *abfd;
2302{
2303  struct xcoff_ar_file_hdr_big fhdr;
2304  bfd_size_type count;
2305  bfd_size_type total_namlen;
2306  file_ptr *offsets;
2307  bfd_boolean makemap;
2308  bfd_boolean hasobjects;
2309  file_ptr prevoff, nextoff;
2310  bfd *current_bfd;
2311  size_t i;
2312  struct xcoff_ar_hdr_big *hdr, ahdr;
2313  bfd_size_type size;
2314  bfd_byte *member_table, *mt;
2315  bfd_vma member_table_size;
2316
2317  memset (&fhdr, 0, SIZEOF_AR_FILE_HDR_BIG);
2318  memcpy (fhdr.magic, XCOFFARMAGBIG, SXCOFFARMAG);
2319
2320  if (bfd_seek (abfd, (file_ptr) SIZEOF_AR_FILE_HDR_BIG, SEEK_SET) != 0)
2321    return FALSE;
2322
2323  /* Calculate count and total_namlen.  */
2324  makemap = bfd_has_map (abfd);
2325  hasobjects = FALSE;
2326  for (current_bfd = abfd->archive_head, count = 0, total_namlen = 0;
2327       current_bfd != NULL;
2328       current_bfd = current_bfd->next, count++)
2329    {
2330      total_namlen += strlen (normalize_filename (current_bfd)) + 1;
2331
2332      if (makemap
2333	  && ! hasobjects
2334	  && bfd_check_format (current_bfd, bfd_object))
2335	hasobjects = TRUE;
2336    }
2337
2338  offsets = NULL;
2339  if (count)
2340    {
2341      offsets = (file_ptr *) bfd_malloc (count * sizeof (file_ptr));
2342      if (offsets == NULL)
2343	return FALSE;
2344    }
2345
2346  prevoff = 0;
2347  nextoff = SIZEOF_AR_FILE_HDR_BIG;
2348  for (current_bfd = abfd->archive_head, i = 0;
2349       current_bfd != NULL;
2350       current_bfd = current_bfd->next, i++)
2351    {
2352      const char *name;
2353      bfd_size_type namlen;
2354      struct xcoff_ar_hdr_big *ahdrp;
2355      bfd_size_type remaining;
2356
2357      name = normalize_filename (current_bfd);
2358      namlen = strlen (name);
2359
2360      if (current_bfd->arelt_data != NULL)
2361	ahdrp = arch_xhdr_big (current_bfd);
2362      else
2363	ahdrp = NULL;
2364
2365      if (ahdrp == NULL)
2366	{
2367	  struct stat s;
2368
2369	  ahdrp = &ahdr;
2370	  /* XXX This should actually be a call to stat64 (at least on
2371	     32-bit machines).
2372	     XXX This call will fail if the original object is not found.  */
2373	  if (stat (bfd_get_filename (current_bfd), &s) != 0)
2374	    {
2375	      bfd_set_error (bfd_error_system_call);
2376	      return FALSE;
2377	    }
2378
2379	  PRINT20 (ahdrp->size, s.st_size);
2380	  PRINT12 (ahdrp->date, s.st_mtime);
2381	  PRINT12 (ahdrp->uid,  s.st_uid);
2382	  PRINT12 (ahdrp->gid,  s.st_gid);
2383	  PRINT12_OCTAL (ahdrp->mode, s.st_mode);
2384
2385	  if (current_bfd->arelt_data == NULL)
2386	    {
2387	      size = sizeof (struct areltdata);
2388	      current_bfd->arelt_data = bfd_alloc (current_bfd, size);
2389	      if (current_bfd->arelt_data == NULL)
2390		return FALSE;
2391	    }
2392
2393	  arch_eltdata (current_bfd)->parsed_size = s.st_size;
2394	}
2395
2396      PRINT20 (ahdrp->prevoff, prevoff);
2397      PRINT4 (ahdrp->namlen, namlen);
2398
2399      /* If the length of the name is odd, we write out the null byte
2400	 after the name as well.  */
2401      namlen = (namlen + 1) &~ (bfd_size_type) 1;
2402
2403      remaining = arelt_size (current_bfd);
2404      size = (SIZEOF_AR_HDR_BIG
2405	      + namlen
2406	      + SXCOFFARFMAG
2407	      + remaining);
2408
2409      BFD_ASSERT (nextoff == bfd_tell (abfd));
2410
2411      /* Check for xcoff shared objects.
2412	 Their text section needs to be aligned wrt the archive file position.
2413	 This requires extra padding before the archive header.  */
2414      if (! do_shared_object_padding (abfd, current_bfd, & nextoff,
2415				      SIZEOF_AR_HDR_BIG + namlen
2416				      + SXCOFFARFMAG))
2417	return FALSE;
2418
2419      offsets[i] = nextoff;
2420
2421      prevoff = nextoff;
2422      nextoff += size + (size & 1);
2423
2424      PRINT20 (ahdrp->nextoff, nextoff);
2425
2426      if ((bfd_bwrite ((PTR) ahdrp, (bfd_size_type) SIZEOF_AR_HDR_BIG, abfd)
2427	   != SIZEOF_AR_HDR_BIG)
2428	  || bfd_bwrite ((PTR) name, (bfd_size_type) namlen, abfd) != namlen
2429	  || (bfd_bwrite ((PTR) XCOFFARFMAG, (bfd_size_type) SXCOFFARFMAG,
2430			  abfd) != SXCOFFARFMAG))
2431	return FALSE;
2432
2433      if (bfd_seek (current_bfd, (file_ptr) 0, SEEK_SET) != 0)
2434	return FALSE;
2435
2436      if (! do_copy (abfd, current_bfd))
2437	return FALSE;
2438
2439      if (! do_pad (abfd, size & 1))
2440	return FALSE;
2441    }
2442
2443  if (count)
2444    {
2445      PRINT20 (fhdr.firstmemoff, offsets[0]);
2446      PRINT20 (fhdr.lastmemoff, prevoff);
2447    }
2448
2449  /* Write out the member table.
2450     Layout :
2451
2452     standard big archive header
2453     0x0000		      ar_size	[0x14]
2454     0x0014		      ar_nxtmem [0x14]
2455     0x0028		      ar_prvmem [0x14]
2456     0x003C		      ar_date	[0x0C]
2457     0x0048		      ar_uid	[0x0C]
2458     0x0054		      ar_gid	[0x0C]
2459     0x0060		      ar_mod	[0x0C]
2460     0x006C		      ar_namelen[0x04]
2461     0x0070		      ar_fmag	[0x02]
2462
2463     Member table
2464     0x0072		      count	[0x14]
2465     0x0086		      offsets	[0x14 * counts]
2466     0x0086 + 0x14 * counts   names	[??]
2467     ??			      pad to even bytes.
2468   */
2469
2470  BFD_ASSERT (nextoff == bfd_tell (abfd));
2471
2472  member_table_size = (SIZEOF_AR_HDR_BIG
2473		       + SXCOFFARFMAG
2474		       + XCOFFARMAGBIG_ELEMENT_SIZE
2475		       + count * XCOFFARMAGBIG_ELEMENT_SIZE
2476		       + total_namlen);
2477
2478  member_table_size += member_table_size & 1;
2479  member_table = NULL;
2480  member_table = (bfd_byte *) bfd_zmalloc (member_table_size);
2481  if (member_table == NULL)
2482    return FALSE;
2483
2484  hdr = (struct xcoff_ar_hdr_big *) member_table;
2485
2486  PRINT20 (hdr->size, (XCOFFARMAGBIG_ELEMENT_SIZE
2487		       + count * XCOFFARMAGBIG_ELEMENT_SIZE
2488		       + total_namlen + (total_namlen & 1)));
2489  if (makemap && hasobjects)
2490    PRINT20 (hdr->nextoff, nextoff + member_table_size);
2491  else
2492    PRINT20 (hdr->nextoff, 0);
2493  PRINT20 (hdr->prevoff, prevoff);
2494  PRINT12 (hdr->date, 0);
2495  PRINT12 (hdr->uid, 0);
2496  PRINT12 (hdr->gid, 0);
2497  PRINT12 (hdr->mode, 0);
2498  PRINT4 (hdr->namlen, 0);
2499
2500  mt = member_table + SIZEOF_AR_HDR_BIG;
2501  memcpy (mt, XCOFFARFMAG, SXCOFFARFMAG);
2502  mt += SXCOFFARFMAG;
2503
2504  PRINT20 (mt, count);
2505  mt += XCOFFARMAGBIG_ELEMENT_SIZE;
2506  for (i = 0; i < (size_t) count; i++)
2507    {
2508      PRINT20 (mt, offsets[i]);
2509      mt += XCOFFARMAGBIG_ELEMENT_SIZE;
2510    }
2511
2512  if (count)
2513    {
2514      free (offsets);
2515      offsets = NULL;
2516    }
2517
2518  for (current_bfd = abfd->archive_head; current_bfd != NULL;
2519       current_bfd = current_bfd->next)
2520    {
2521      const char *name;
2522      size_t namlen;
2523
2524      name = normalize_filename (current_bfd);
2525      namlen = sprintf (mt, "%s", name);
2526      mt += namlen + 1;
2527    }
2528
2529  if (bfd_bwrite (member_table, member_table_size, abfd) != member_table_size)
2530    return FALSE;
2531
2532  free (member_table);
2533  member_table = NULL;
2534
2535  PRINT20 (fhdr.memoff, nextoff);
2536
2537  prevoff = nextoff;
2538  nextoff += member_table_size;
2539
2540  /* Write out the armap, if appropriate.  */
2541
2542  if (! makemap || ! hasobjects)
2543    PRINT20 (fhdr.symoff, 0);
2544  else
2545    {
2546      BFD_ASSERT (nextoff == bfd_tell (abfd));
2547
2548      /* Save nextoff in fhdr.symoff so the armap routine can use it.  */
2549      PRINT20 (fhdr.symoff, nextoff);
2550
2551      bfd_ardata (abfd)->tdata = (PTR) &fhdr;
2552      if (! _bfd_compute_and_write_armap (abfd, 0))
2553	return FALSE;
2554    }
2555
2556  /* Write out the archive file header.  */
2557
2558  if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0
2559      || (bfd_bwrite ((PTR) &fhdr, (bfd_size_type) SIZEOF_AR_FILE_HDR_BIG,
2560		      abfd) != SIZEOF_AR_FILE_HDR_BIG))
2561    return FALSE;
2562
2563  return TRUE;
2564}
2565
2566bfd_boolean
2567_bfd_xcoff_write_archive_contents (abfd)
2568     bfd *abfd;
2569{
2570  if (! xcoff_big_format_p (abfd))
2571    return xcoff_write_archive_contents_old (abfd);
2572  else
2573    return xcoff_write_archive_contents_big (abfd);
2574}
2575
2576/* We can't use the usual coff_sizeof_headers routine, because AIX
2577   always uses an a.out header.  */
2578
2579int
2580_bfd_xcoff_sizeof_headers (abfd, reloc)
2581     bfd *abfd;
2582     bfd_boolean reloc ATTRIBUTE_UNUSED;
2583{
2584  int size;
2585
2586  size = FILHSZ;
2587  if (xcoff_data (abfd)->full_aouthdr)
2588    size += AOUTSZ;
2589  else
2590    size += SMALL_AOUTSZ;
2591  size += abfd->section_count * SCNHSZ;
2592  return size;
2593}
2594
2595/* Routines to swap information in the XCOFF .loader section.  If we
2596   ever need to write an XCOFF loader, this stuff will need to be
2597   moved to another file shared by the linker (which XCOFF calls the
2598   ``binder'') and the loader.  */
2599
2600/* Swap in the ldhdr structure.  */
2601
2602static void
2603xcoff_swap_ldhdr_in (abfd, s, dst)
2604     bfd *abfd;
2605     const PTR s;
2606     struct internal_ldhdr *dst;
2607{
2608  const struct external_ldhdr *src = (const struct external_ldhdr *) s;
2609
2610  dst->l_version = bfd_get_32 (abfd, src->l_version);
2611  dst->l_nsyms = bfd_get_32 (abfd, src->l_nsyms);
2612  dst->l_nreloc = bfd_get_32 (abfd, src->l_nreloc);
2613  dst->l_istlen = bfd_get_32 (abfd, src->l_istlen);
2614  dst->l_nimpid = bfd_get_32 (abfd, src->l_nimpid);
2615  dst->l_impoff = bfd_get_32 (abfd, src->l_impoff);
2616  dst->l_stlen = bfd_get_32 (abfd, src->l_stlen);
2617  dst->l_stoff = bfd_get_32 (abfd, src->l_stoff);
2618}
2619
2620/* Swap out the ldhdr structure.  */
2621
2622static void
2623xcoff_swap_ldhdr_out (abfd, src, d)
2624     bfd *abfd;
2625     const struct internal_ldhdr *src;
2626     PTR d;
2627{
2628  struct external_ldhdr *dst = (struct external_ldhdr *) d;
2629
2630  bfd_put_32 (abfd, (bfd_vma) src->l_version, dst->l_version);
2631  bfd_put_32 (abfd, src->l_nsyms, dst->l_nsyms);
2632  bfd_put_32 (abfd, src->l_nreloc, dst->l_nreloc);
2633  bfd_put_32 (abfd, src->l_istlen, dst->l_istlen);
2634  bfd_put_32 (abfd, src->l_nimpid, dst->l_nimpid);
2635  bfd_put_32 (abfd, src->l_impoff, dst->l_impoff);
2636  bfd_put_32 (abfd, src->l_stlen, dst->l_stlen);
2637  bfd_put_32 (abfd, src->l_stoff, dst->l_stoff);
2638}
2639
2640/* Swap in the ldsym structure.  */
2641
2642static void
2643xcoff_swap_ldsym_in (abfd, s, dst)
2644     bfd *abfd;
2645     const PTR s;
2646     struct internal_ldsym *dst;
2647{
2648  const struct external_ldsym *src = (const struct external_ldsym *) s;
2649
2650  if (bfd_get_32 (abfd, src->_l._l_l._l_zeroes) != 0) {
2651    memcpy (dst->_l._l_name, src->_l._l_name, SYMNMLEN);
2652  } else {
2653    dst->_l._l_l._l_zeroes = 0;
2654    dst->_l._l_l._l_offset = bfd_get_32 (abfd, src->_l._l_l._l_offset);
2655  }
2656  dst->l_value = bfd_get_32 (abfd, src->l_value);
2657  dst->l_scnum = bfd_get_16 (abfd, src->l_scnum);
2658  dst->l_smtype = bfd_get_8 (abfd, src->l_smtype);
2659  dst->l_smclas = bfd_get_8 (abfd, src->l_smclas);
2660  dst->l_ifile = bfd_get_32 (abfd, src->l_ifile);
2661  dst->l_parm = bfd_get_32 (abfd, src->l_parm);
2662}
2663
2664/* Swap out the ldsym structure.  */
2665
2666static void
2667xcoff_swap_ldsym_out (abfd, src, d)
2668     bfd *abfd;
2669     const struct internal_ldsym *src;
2670     PTR d;
2671{
2672  struct external_ldsym *dst = (struct external_ldsym *) d;
2673
2674  if (src->_l._l_l._l_zeroes != 0)
2675    memcpy (dst->_l._l_name, src->_l._l_name, SYMNMLEN);
2676  else
2677    {
2678      bfd_put_32 (abfd, (bfd_vma) 0, dst->_l._l_l._l_zeroes);
2679      bfd_put_32 (abfd, (bfd_vma) src->_l._l_l._l_offset,
2680		  dst->_l._l_l._l_offset);
2681    }
2682  bfd_put_32 (abfd, src->l_value, dst->l_value);
2683  bfd_put_16 (abfd, (bfd_vma) src->l_scnum, dst->l_scnum);
2684  bfd_put_8 (abfd, src->l_smtype, dst->l_smtype);
2685  bfd_put_8 (abfd, src->l_smclas, dst->l_smclas);
2686  bfd_put_32 (abfd, src->l_ifile, dst->l_ifile);
2687  bfd_put_32 (abfd, src->l_parm, dst->l_parm);
2688}
2689
2690static void
2691xcoff_swap_reloc_in (abfd, s, d)
2692     bfd *abfd;
2693     PTR s;
2694     PTR d;
2695{
2696  struct external_reloc *src = (struct external_reloc *) s;
2697  struct internal_reloc *dst = (struct internal_reloc *) d;
2698
2699  memset (dst, 0, sizeof (struct internal_reloc));
2700
2701  dst->r_vaddr = bfd_get_32 (abfd, src->r_vaddr);
2702  dst->r_symndx = bfd_get_32 (abfd, src->r_symndx);
2703  dst->r_size = bfd_get_8 (abfd, src->r_size);
2704  dst->r_type = bfd_get_8 (abfd, src->r_type);
2705}
2706
2707static unsigned int
2708xcoff_swap_reloc_out (abfd, s, d)
2709     bfd *abfd;
2710     PTR s;
2711     PTR d;
2712{
2713  struct internal_reloc *src = (struct internal_reloc *) s;
2714  struct external_reloc *dst = (struct external_reloc *) d;
2715
2716  bfd_put_32 (abfd, src->r_vaddr, dst->r_vaddr);
2717  bfd_put_32 (abfd, src->r_symndx, dst->r_symndx);
2718  bfd_put_8 (abfd, src->r_type, dst->r_type);
2719  bfd_put_8 (abfd, src->r_size, dst->r_size);
2720
2721  return bfd_coff_relsz (abfd);
2722}
2723
2724/* Swap in the ldrel structure.  */
2725
2726static void
2727xcoff_swap_ldrel_in (abfd, s, dst)
2728     bfd *abfd;
2729     const PTR s;
2730     struct internal_ldrel *dst;
2731{
2732  const struct external_ldrel *src = (const struct external_ldrel *) s;
2733
2734  dst->l_vaddr = bfd_get_32 (abfd, src->l_vaddr);
2735  dst->l_symndx = bfd_get_32 (abfd, src->l_symndx);
2736  dst->l_rtype = bfd_get_16 (abfd, src->l_rtype);
2737  dst->l_rsecnm = bfd_get_16 (abfd, src->l_rsecnm);
2738}
2739
2740/* Swap out the ldrel structure.  */
2741
2742static void
2743xcoff_swap_ldrel_out (abfd, src, d)
2744     bfd *abfd;
2745     const struct internal_ldrel *src;
2746     PTR d;
2747{
2748  struct external_ldrel *dst = (struct external_ldrel *) d;
2749
2750  bfd_put_32 (abfd, src->l_vaddr, dst->l_vaddr);
2751  bfd_put_32 (abfd, src->l_symndx, dst->l_symndx);
2752  bfd_put_16 (abfd, (bfd_vma) src->l_rtype, dst->l_rtype);
2753  bfd_put_16 (abfd, (bfd_vma) src->l_rsecnm, dst->l_rsecnm);
2754}
2755
2756
2757bfd_boolean
2758xcoff_reloc_type_noop (input_bfd, input_section, output_bfd, rel, sym, howto,
2759		       val, addend, relocation, contents)
2760     bfd *input_bfd ATTRIBUTE_UNUSED;
2761     asection *input_section ATTRIBUTE_UNUSED;
2762     bfd *output_bfd ATTRIBUTE_UNUSED;
2763     struct internal_reloc *rel ATTRIBUTE_UNUSED;
2764     struct internal_syment *sym ATTRIBUTE_UNUSED;
2765     struct reloc_howto_struct *howto ATTRIBUTE_UNUSED;
2766     bfd_vma val ATTRIBUTE_UNUSED;
2767     bfd_vma addend ATTRIBUTE_UNUSED;
2768     bfd_vma *relocation ATTRIBUTE_UNUSED;
2769     bfd_byte *contents ATTRIBUTE_UNUSED;
2770{
2771  return TRUE;
2772}
2773
2774bfd_boolean
2775xcoff_reloc_type_fail (input_bfd, input_section, output_bfd, rel, sym, howto,
2776		       val, addend, relocation, contents)
2777     bfd *input_bfd;
2778     asection *input_section ATTRIBUTE_UNUSED;
2779     bfd *output_bfd ATTRIBUTE_UNUSED;
2780     struct internal_reloc *rel;
2781     struct internal_syment *sym ATTRIBUTE_UNUSED;
2782     struct reloc_howto_struct *howto ATTRIBUTE_UNUSED;
2783     bfd_vma val ATTRIBUTE_UNUSED;
2784     bfd_vma addend ATTRIBUTE_UNUSED;
2785     bfd_vma *relocation ATTRIBUTE_UNUSED;
2786     bfd_byte *contents ATTRIBUTE_UNUSED;
2787{
2788  (*_bfd_error_handler)
2789    (_("%s: unsupported relocation type 0x%02x"),
2790     bfd_get_filename (input_bfd), (unsigned int) rel->r_type);
2791  bfd_set_error (bfd_error_bad_value);
2792  return FALSE;
2793}
2794
2795bfd_boolean
2796xcoff_reloc_type_pos (input_bfd, input_section, output_bfd, rel, sym, howto,
2797		      val, addend, relocation, contents)
2798     bfd *input_bfd ATTRIBUTE_UNUSED;
2799     asection *input_section ATTRIBUTE_UNUSED;
2800     bfd *output_bfd ATTRIBUTE_UNUSED;
2801     struct internal_reloc *rel ATTRIBUTE_UNUSED;
2802     struct internal_syment *sym ATTRIBUTE_UNUSED;
2803     struct reloc_howto_struct *howto ATTRIBUTE_UNUSED;
2804     bfd_vma val;
2805     bfd_vma addend;
2806     bfd_vma *relocation;
2807     bfd_byte *contents ATTRIBUTE_UNUSED;
2808{
2809  *relocation = val + addend;
2810  return TRUE;
2811}
2812
2813bfd_boolean
2814xcoff_reloc_type_neg (input_bfd, input_section, output_bfd, rel, sym, howto,
2815		      val, addend, relocation, contents)
2816     bfd *input_bfd ATTRIBUTE_UNUSED;
2817     asection *input_section ATTRIBUTE_UNUSED;
2818     bfd *output_bfd ATTRIBUTE_UNUSED;
2819     struct internal_reloc *rel ATTRIBUTE_UNUSED;
2820     struct internal_syment *sym ATTRIBUTE_UNUSED;
2821     struct reloc_howto_struct *howto ATTRIBUTE_UNUSED;
2822     bfd_vma val;
2823     bfd_vma addend;
2824     bfd_vma *relocation;
2825     bfd_byte *contents ATTRIBUTE_UNUSED;
2826{
2827  *relocation = addend - val;
2828  return TRUE;
2829}
2830
2831bfd_boolean
2832xcoff_reloc_type_rel (input_bfd, input_section, output_bfd, rel, sym, howto,
2833		      val, addend, relocation, contents)
2834     bfd *input_bfd ATTRIBUTE_UNUSED;
2835     asection *input_section;
2836     bfd *output_bfd ATTRIBUTE_UNUSED;
2837     struct internal_reloc *rel ATTRIBUTE_UNUSED;
2838     struct internal_syment *sym ATTRIBUTE_UNUSED;
2839     struct reloc_howto_struct *howto;
2840     bfd_vma val;
2841     bfd_vma addend;
2842     bfd_vma *relocation;
2843     bfd_byte *contents ATTRIBUTE_UNUSED;
2844{
2845  howto->pc_relative = TRUE;
2846
2847  /* A PC relative reloc includes the section address.  */
2848  addend += input_section->vma;
2849
2850  *relocation = val + addend;
2851  *relocation -= (input_section->output_section->vma
2852		  + input_section->output_offset);
2853  return TRUE;
2854}
2855
2856bfd_boolean
2857xcoff_reloc_type_toc (input_bfd, input_section, output_bfd, rel, sym, howto,
2858		      val, addend, relocation, contents)
2859     bfd *input_bfd;
2860     asection *input_section ATTRIBUTE_UNUSED;
2861     bfd *output_bfd;
2862     struct internal_reloc *rel;
2863     struct internal_syment *sym;
2864     struct reloc_howto_struct *howto ATTRIBUTE_UNUSED;
2865     bfd_vma val;
2866     bfd_vma addend ATTRIBUTE_UNUSED;
2867     bfd_vma *relocation;
2868     bfd_byte *contents ATTRIBUTE_UNUSED;
2869{
2870  struct xcoff_link_hash_entry *h;
2871
2872  if (0 > rel->r_symndx)
2873    return FALSE;
2874
2875  h = obj_xcoff_sym_hashes (input_bfd)[rel->r_symndx];
2876
2877  if (h != NULL && h->smclas != XMC_TD)
2878    {
2879      if (h->toc_section == NULL)
2880	{
2881	  (*_bfd_error_handler)
2882	    (_("%s: TOC reloc at 0x%x to symbol `%s' with no TOC entry"),
2883	     bfd_get_filename (input_bfd), rel->r_vaddr,
2884	     h->root.root.string);
2885	  bfd_set_error (bfd_error_bad_value);
2886	  return FALSE;
2887	}
2888
2889      BFD_ASSERT ((h->flags & XCOFF_SET_TOC) == 0);
2890      val = (h->toc_section->output_section->vma
2891	      + h->toc_section->output_offset);
2892    }
2893
2894  *relocation = ((val - xcoff_data (output_bfd)->toc)
2895		 - (sym->n_value - xcoff_data (input_bfd)->toc));
2896  return TRUE;
2897}
2898
2899bfd_boolean
2900xcoff_reloc_type_ba (input_bfd, input_section, output_bfd, rel, sym, howto,
2901		     val, addend, relocation, contents)
2902     bfd *input_bfd ATTRIBUTE_UNUSED;
2903     asection *input_section ATTRIBUTE_UNUSED;
2904     bfd *output_bfd ATTRIBUTE_UNUSED;
2905     struct internal_reloc *rel ATTRIBUTE_UNUSED;
2906     struct internal_syment *sym ATTRIBUTE_UNUSED;
2907     struct reloc_howto_struct *howto;
2908     bfd_vma val;
2909     bfd_vma addend;
2910     bfd_vma *relocation;
2911     bfd_byte *contents ATTRIBUTE_UNUSED;
2912{
2913  howto->src_mask &= ~3;
2914  howto->dst_mask = howto->src_mask;
2915
2916  *relocation = val + addend;
2917
2918  return TRUE;
2919}
2920
2921static bfd_boolean
2922xcoff_reloc_type_br (input_bfd, input_section, output_bfd, rel, sym, howto,
2923		     val, addend, relocation, contents)
2924     bfd *input_bfd;
2925     asection *input_section;
2926     bfd *output_bfd ATTRIBUTE_UNUSED;
2927     struct internal_reloc *rel;
2928     struct internal_syment *sym ATTRIBUTE_UNUSED;
2929     struct reloc_howto_struct *howto;
2930     bfd_vma val;
2931     bfd_vma addend;
2932     bfd_vma *relocation;
2933     bfd_byte *contents;
2934{
2935  struct xcoff_link_hash_entry *h;
2936
2937  if (0 > rel->r_symndx)
2938    return FALSE;
2939
2940  h = obj_xcoff_sym_hashes (input_bfd)[rel->r_symndx];
2941
2942  /* If we see an R_BR or R_RBR reloc which is jumping to global
2943     linkage code, and it is followed by an appropriate cror nop
2944     instruction, we replace the cror with lwz r2,20(r1).  This
2945     restores the TOC after the glink code.  Contrariwise, if the
2946     call is followed by a lwz r2,20(r1), but the call is not
2947     going to global linkage code, we can replace the load with a
2948     cror.  */
2949  if (NULL != h
2950      && bfd_link_hash_defined == h->root.type
2951      && rel->r_vaddr - input_section->vma + 8 <= input_section->size)
2952    {
2953      bfd_byte *pnext;
2954      unsigned long next;
2955
2956      pnext = contents + (rel->r_vaddr - input_section->vma) + 4;
2957      next = bfd_get_32 (input_bfd, pnext);
2958
2959      /* The _ptrgl function is magic.  It is used by the AIX
2960	 compiler to call a function through a pointer.  */
2961      if (h->smclas == XMC_GL || strcmp (h->root.root.string, "._ptrgl") == 0)
2962	{
2963	  if (next == 0x4def7b82			/* cror 15,15,15 */
2964	      || next == 0x4ffffb82			/* cror 31,31,31 */
2965	      || next == 0x60000000)			/* ori r0,r0,0 */
2966	    bfd_put_32 (input_bfd, 0x80410014, pnext);	/* lwz r1,20(r1) */
2967
2968	}
2969      else
2970	{
2971	  if (next == 0x80410014)			/* lwz r1,20(r1) */
2972	    bfd_put_32 (input_bfd, 0x60000000, pnext);	/* ori r0,r0,0 */
2973	}
2974    }
2975  else if (NULL != h && bfd_link_hash_undefined == h->root.type)
2976    {
2977      /* Normally, this relocation is against a defined symbol.  In the
2978	 case where this is a partial link and the output section offset
2979	 is greater than 2^25, the linker will return an invalid error
2980	 message that the relocation has been truncated.  Yes it has been
2981	 truncated but no it not important.  For this case, disable the
2982	 overflow checking. */
2983
2984      howto->complain_on_overflow = complain_overflow_dont;
2985    }
2986
2987  howto->pc_relative = TRUE;
2988  howto->src_mask &= ~3;
2989  howto->dst_mask = howto->src_mask;
2990
2991  /* A PC relative reloc includes the section address.  */
2992  addend += input_section->vma;
2993
2994  *relocation = val + addend;
2995  *relocation -= (input_section->output_section->vma
2996		  + input_section->output_offset);
2997  return TRUE;
2998}
2999
3000bfd_boolean
3001xcoff_reloc_type_crel (input_bfd, input_section, output_bfd, rel, sym, howto,
3002		       val, addend, relocation, contents)
3003     bfd *input_bfd ATTRIBUTE_UNUSED;
3004     asection *input_section;
3005     bfd *output_bfd ATTRIBUTE_UNUSED;
3006     struct internal_reloc *rel ATTRIBUTE_UNUSED;
3007     struct internal_syment *sym ATTRIBUTE_UNUSED;
3008     struct reloc_howto_struct *howto;
3009     bfd_vma val ATTRIBUTE_UNUSED;
3010     bfd_vma addend;
3011     bfd_vma *relocation;
3012     bfd_byte *contents ATTRIBUTE_UNUSED;
3013{
3014  howto->pc_relative = TRUE;
3015  howto->src_mask &= ~3;
3016  howto->dst_mask = howto->src_mask;
3017
3018  /* A PC relative reloc includes the section address.  */
3019  addend += input_section->vma;
3020
3021  *relocation = val + addend;
3022  *relocation -= (input_section->output_section->vma
3023		  + input_section->output_offset);
3024  return TRUE;
3025}
3026
3027static bfd_boolean
3028xcoff_complain_overflow_dont_func (input_bfd, val, relocation, howto)
3029     bfd *input_bfd ATTRIBUTE_UNUSED;
3030     bfd_vma val ATTRIBUTE_UNUSED;
3031     bfd_vma relocation ATTRIBUTE_UNUSED;
3032     struct reloc_howto_struct *howto ATTRIBUTE_UNUSED;
3033{
3034  return FALSE;
3035}
3036
3037static bfd_boolean
3038xcoff_complain_overflow_bitfield_func (input_bfd, val, relocation, howto)
3039     bfd *input_bfd;
3040     bfd_vma val;
3041     bfd_vma relocation;
3042     struct reloc_howto_struct *howto;
3043{
3044  bfd_vma addrmask, fieldmask, signmask, ss;
3045  bfd_vma a, b, sum;
3046
3047  /* Get the values to be added together.  For signed and unsigned
3048     relocations, we assume that all values should be truncated to
3049     the size of an address.  For bitfields, all the bits matter.
3050     See also bfd_check_overflow.  */
3051  fieldmask = N_ONES (howto->bitsize);
3052  addrmask = N_ONES (bfd_arch_bits_per_address (input_bfd)) | fieldmask;
3053  a = relocation;
3054  b = val & howto->src_mask;
3055
3056  /* Much like unsigned, except no trimming with addrmask.  In
3057     addition, the sum overflows if there is a carry out of
3058     the bfd_vma, i.e., the sum is less than either input
3059     operand.  */
3060  a >>= howto->rightshift;
3061  b >>= howto->bitpos;
3062
3063  /* Bitfields are sometimes used for signed numbers; for
3064     example, a 13-bit field sometimes represents values in
3065     0..8191 and sometimes represents values in -4096..4095.
3066     If the field is signed and a is -4095 (0x1001) and b is
3067     -1 (0x1fff), the sum is -4096 (0x1000), but (0x1001 +
3068     0x1fff is 0x3000).  It's not clear how to handle this
3069     everywhere, since there is not way to know how many bits
3070     are significant in the relocation, but the original code
3071     assumed that it was fully sign extended, and we will keep
3072     that assumption.  */
3073  signmask = (fieldmask >> 1) + 1;
3074
3075  if ((a & ~ fieldmask) != 0)
3076    {
3077      /* Some bits out of the field are set.  This might not
3078	 be a problem: if this is a signed bitfield, it is OK
3079	 iff all the high bits are set, including the sign
3080	 bit.  We'll try setting all but the most significant
3081	 bit in the original relocation value: if this is all
3082	 ones, we are OK, assuming a signed bitfield.  */
3083      ss = (signmask << howto->rightshift) - 1;
3084      if ((ss | relocation) != ~ (bfd_vma) 0)
3085	return TRUE;
3086      a &= fieldmask;
3087    }
3088
3089  /* We just assume (b & ~ fieldmask) == 0.  */
3090
3091  /* We explicitly permit wrap around if this relocation
3092     covers the high bit of an address.  The Linux kernel
3093     relies on it, and it is the only way to write assembler
3094     code which can run when loaded at a location 0x80000000
3095     away from the location at which it is linked.  */
3096  if (howto->bitsize + howto->rightshift
3097      == bfd_arch_bits_per_address (input_bfd))
3098    return FALSE;
3099
3100  sum = a + b;
3101  if (sum < a || (sum & ~ fieldmask) != 0)
3102    {
3103      /* There was a carry out, or the field overflow.  Test
3104	 for signed operands again.  Here is the overflow test
3105	 is as for complain_overflow_signed.  */
3106      if (((~ (a ^ b)) & (a ^ sum)) & signmask)
3107	return TRUE;
3108    }
3109
3110  return FALSE;
3111}
3112
3113static bfd_boolean
3114xcoff_complain_overflow_signed_func (input_bfd, val, relocation, howto)
3115     bfd *input_bfd;
3116     bfd_vma val;
3117     bfd_vma relocation;
3118     struct reloc_howto_struct *howto;
3119{
3120  bfd_vma addrmask, fieldmask, signmask, ss;
3121  bfd_vma a, b, sum;
3122
3123  /* Get the values to be added together.  For signed and unsigned
3124     relocations, we assume that all values should be truncated to
3125     the size of an address.  For bitfields, all the bits matter.
3126     See also bfd_check_overflow.  */
3127  fieldmask = N_ONES (howto->bitsize);
3128  addrmask = N_ONES (bfd_arch_bits_per_address (input_bfd)) | fieldmask;
3129  a = relocation;
3130  b = val & howto->src_mask;
3131
3132  a = (a & addrmask) >> howto->rightshift;
3133
3134  /* If any sign bits are set, all sign bits must be set.
3135     That is, A must be a valid negative address after
3136     shifting.  */
3137  signmask = ~ (fieldmask >> 1);
3138  ss = a & signmask;
3139  if (ss != 0 && ss != ((addrmask >> howto->rightshift) & signmask))
3140    return TRUE;
3141
3142  /* We only need this next bit of code if the sign bit of B
3143     is below the sign bit of A.  This would only happen if
3144     SRC_MASK had fewer bits than BITSIZE.  Note that if
3145     SRC_MASK has more bits than BITSIZE, we can get into
3146     trouble; we would need to verify that B is in range, as
3147     we do for A above.  */
3148  signmask = ((~ howto->src_mask) >> 1) & howto->src_mask;
3149  if ((b & signmask) != 0)
3150    {
3151      /* Set all the bits above the sign bit.  */
3152      b -= signmask <<= 1;
3153    }
3154
3155  b = (b & addrmask) >> howto->bitpos;
3156
3157  /* Now we can do the addition.  */
3158  sum = a + b;
3159
3160  /* See if the result has the correct sign.  Bits above the
3161     sign bit are junk now; ignore them.  If the sum is
3162     positive, make sure we did not have all negative inputs;
3163     if the sum is negative, make sure we did not have all
3164     positive inputs.  The test below looks only at the sign
3165     bits, and it really just
3166     SIGN (A) == SIGN (B) && SIGN (A) != SIGN (SUM)
3167  */
3168  signmask = (fieldmask >> 1) + 1;
3169  if (((~ (a ^ b)) & (a ^ sum)) & signmask)
3170    return TRUE;
3171
3172  return FALSE;
3173}
3174
3175static bfd_boolean
3176xcoff_complain_overflow_unsigned_func (input_bfd, val, relocation, howto)
3177     bfd *input_bfd;
3178     bfd_vma val;
3179     bfd_vma relocation;
3180     struct reloc_howto_struct *howto;
3181{
3182  bfd_vma addrmask, fieldmask;
3183  bfd_vma a, b, sum;
3184
3185  /* Get the values to be added together.  For signed and unsigned
3186     relocations, we assume that all values should be truncated to
3187     the size of an address.  For bitfields, all the bits matter.
3188     See also bfd_check_overflow.  */
3189  fieldmask = N_ONES (howto->bitsize);
3190  addrmask = N_ONES (bfd_arch_bits_per_address (input_bfd)) | fieldmask;
3191  a = relocation;
3192  b = val & howto->src_mask;
3193
3194  /* Checking for an unsigned overflow is relatively easy:
3195     trim the addresses and add, and trim the result as well.
3196     Overflow is normally indicated when the result does not
3197     fit in the field.  However, we also need to consider the
3198     case when, e.g., fieldmask is 0x7fffffff or smaller, an
3199     input is 0x80000000, and bfd_vma is only 32 bits; then we
3200     will get sum == 0, but there is an overflow, since the
3201     inputs did not fit in the field.  Instead of doing a
3202     separate test, we can check for this by or-ing in the
3203     operands when testing for the sum overflowing its final
3204     field.  */
3205  a = (a & addrmask) >> howto->rightshift;
3206  b = (b & addrmask) >> howto->bitpos;
3207  sum = (a + b) & addrmask;
3208  if ((a | b | sum) & ~ fieldmask)
3209    return TRUE;
3210
3211  return FALSE;
3212}
3213
3214/* This is the relocation function for the RS/6000/POWER/PowerPC.
3215   This is currently the only processor which uses XCOFF; I hope that
3216   will never change.
3217
3218   I took the relocation type definitions from two documents:
3219   the PowerPC AIX Version 4 Application Binary Interface, First
3220   Edition (April 1992), and the PowerOpen ABI, Big-Endian
3221   32-Bit Hardware Implementation (June 30, 1994).  Differences
3222   between the documents are noted below.
3223
3224   Unsupported r_type's
3225
3226   R_RTB:
3227   R_RRTBI:
3228   R_RRTBA:
3229
3230   These relocs are defined by the PowerPC ABI to be
3231   relative branches which use half of the difference
3232   between the symbol and the program counter.  I can't
3233   quite figure out when this is useful.  These relocs are
3234   not defined by the PowerOpen ABI.
3235
3236   Supported r_type's
3237
3238   R_POS:
3239   Simple positive relocation.
3240
3241   R_NEG:
3242   Simple negative relocation.
3243
3244   R_REL:
3245   Simple PC relative relocation.
3246
3247   R_TOC:
3248   TOC relative relocation.  The value in the instruction in
3249   the input file is the offset from the input file TOC to
3250   the desired location.  We want the offset from the final
3251   TOC to the desired location.  We have:
3252   isym = iTOC + in
3253   iinsn = in + o
3254   osym = oTOC + on
3255   oinsn = on + o
3256   so we must change insn by on - in.
3257
3258   R_GL:
3259   GL linkage relocation.  The value of this relocation
3260   is the address of the entry in the TOC section.
3261
3262   R_TCL:
3263   Local object TOC address.  I can't figure out the
3264   difference between this and case R_GL.
3265
3266   R_TRL:
3267   TOC relative relocation.  A TOC relative load instruction
3268   which may be changed to a load address instruction.
3269   FIXME: We don't currently implement this optimization.
3270
3271   R_TRLA:
3272   TOC relative relocation.  This is a TOC relative load
3273   address instruction which may be changed to a load
3274   instruction.  FIXME: I don't know if this is the correct
3275   implementation.
3276
3277   R_BA:
3278   Absolute branch.  We don't want to mess with the lower
3279   two bits of the instruction.
3280
3281   R_CAI:
3282   The PowerPC ABI defines this as an absolute call which
3283   may be modified to become a relative call.  The PowerOpen
3284   ABI does not define this relocation type.
3285
3286   R_RBA:
3287   Absolute branch which may be modified to become a
3288   relative branch.
3289
3290   R_RBAC:
3291   The PowerPC ABI defines this as an absolute branch to a
3292   fixed address which may be modified to an absolute branch
3293   to a symbol.  The PowerOpen ABI does not define this
3294   relocation type.
3295
3296   R_RBRC:
3297   The PowerPC ABI defines this as an absolute branch to a
3298   fixed address which may be modified to a relative branch.
3299   The PowerOpen ABI does not define this relocation type.
3300
3301   R_BR:
3302   Relative branch.  We don't want to mess with the lower
3303   two bits of the instruction.
3304
3305   R_CREL:
3306   The PowerPC ABI defines this as a relative call which may
3307   be modified to become an absolute call.  The PowerOpen
3308   ABI does not define this relocation type.
3309
3310   R_RBR:
3311   A relative branch which may be modified to become an
3312   absolute branch.  FIXME: We don't implement this,
3313   although we should for symbols of storage mapping class
3314   XMC_XO.
3315
3316   R_RL:
3317   The PowerPC AIX ABI describes this as a load which may be
3318   changed to a load address.  The PowerOpen ABI says this
3319   is the same as case R_POS.
3320
3321   R_RLA:
3322   The PowerPC AIX ABI describes this as a load address
3323   which may be changed to a load.  The PowerOpen ABI says
3324   this is the same as R_POS.
3325*/
3326
3327bfd_boolean
3328xcoff_ppc_relocate_section (output_bfd, info, input_bfd,
3329			    input_section, contents, relocs, syms,
3330			    sections)
3331     bfd *output_bfd;
3332     struct bfd_link_info *info;
3333     bfd *input_bfd;
3334     asection *input_section;
3335     bfd_byte *contents;
3336     struct internal_reloc *relocs;
3337     struct internal_syment *syms;
3338     asection **sections;
3339{
3340  struct internal_reloc *rel;
3341  struct internal_reloc *relend;
3342
3343  rel = relocs;
3344  relend = rel + input_section->reloc_count;
3345  for (; rel < relend; rel++)
3346    {
3347      long symndx;
3348      struct xcoff_link_hash_entry *h;
3349      struct internal_syment *sym;
3350      bfd_vma addend;
3351      bfd_vma val;
3352      struct reloc_howto_struct howto;
3353      bfd_vma relocation;
3354      bfd_vma value_to_relocate;
3355      bfd_vma address;
3356      bfd_byte *location;
3357
3358      /* Relocation type R_REF is a special relocation type which is
3359	 merely used to prevent garbage collection from occurring for
3360	 the csect including the symbol which it references.  */
3361      if (rel->r_type == R_REF)
3362	continue;
3363
3364      /* howto */
3365      howto.type = rel->r_type;
3366      howto.rightshift = 0;
3367      howto.bitsize = (rel->r_size & 0x1f) + 1;
3368      howto.size = howto.bitsize > 16 ? 2 : 1;
3369      howto.pc_relative = FALSE;
3370      howto.bitpos = 0;
3371      howto.complain_on_overflow = (rel->r_size & 0x80
3372				    ? complain_overflow_signed
3373				    : complain_overflow_bitfield);
3374      howto.special_function = NULL;
3375      howto.name = "internal";
3376      howto.partial_inplace = TRUE;
3377      howto.src_mask = howto.dst_mask = N_ONES (howto.bitsize);
3378      howto.pcrel_offset = FALSE;
3379
3380      /* symbol */
3381      val = 0;
3382      addend = 0;
3383      h = NULL;
3384      sym = NULL;
3385      symndx = rel->r_symndx;
3386
3387      if (-1 != symndx)
3388	{
3389	  asection *sec;
3390
3391	  h = obj_xcoff_sym_hashes (input_bfd)[symndx];
3392	  sym = syms + symndx;
3393	  addend = - sym->n_value;
3394
3395	  if (NULL == h)
3396	    {
3397	      sec = sections[symndx];
3398	      /* Hack to make sure we use the right TOC anchor value
3399		 if this reloc is against the TOC anchor.  */
3400	      if (sec->name[3] == '0'
3401		  && strcmp (sec->name, ".tc0") == 0)
3402		val = xcoff_data (output_bfd)->toc;
3403	      else
3404		val = (sec->output_section->vma
3405		       + sec->output_offset
3406		       + sym->n_value
3407		       - sec->vma);
3408	    }
3409	  else
3410	    {
3411	      if (h->root.type == bfd_link_hash_defined
3412		  || h->root.type == bfd_link_hash_defweak)
3413		{
3414		  sec = h->root.u.def.section;
3415		  val = (h->root.u.def.value
3416			 + sec->output_section->vma
3417			 + sec->output_offset);
3418		}
3419	      else if (h->root.type == bfd_link_hash_common)
3420		{
3421		  sec = h->root.u.c.p->section;
3422		  val = (sec->output_section->vma
3423			 + sec->output_offset);
3424
3425		}
3426	      else if ((0 == (h->flags & (XCOFF_DEF_DYNAMIC | XCOFF_IMPORT)))
3427		       && ! info->relocatable)
3428		{
3429		  if (! ((*info->callbacks->undefined_symbol)
3430			 (info, h->root.root.string, input_bfd, input_section,
3431			  rel->r_vaddr - input_section->vma, TRUE)))
3432		    return FALSE;
3433
3434		  /* Don't try to process the reloc.  It can't help, and
3435		     it may generate another error.  */
3436		  continue;
3437		}
3438	    }
3439	}
3440
3441      if (rel->r_type >= XCOFF_MAX_CALCULATE_RELOCATION
3442	  || !((*xcoff_calculate_relocation[rel->r_type])
3443	       (input_bfd, input_section, output_bfd, rel, sym, &howto, val,
3444		addend, &relocation, contents)))
3445	return FALSE;
3446
3447      /* address */
3448      address = rel->r_vaddr - input_section->vma;
3449      location = contents + address;
3450
3451      if (address > input_section->size)
3452	abort ();
3453
3454      /* Get the value we are going to relocate.  */
3455      if (1 == howto.size)
3456	value_to_relocate = bfd_get_16 (input_bfd, location);
3457      else
3458	value_to_relocate = bfd_get_32 (input_bfd, location);
3459
3460      /* overflow.
3461
3462	 FIXME: We may drop bits during the addition
3463	 which we don't check for.  We must either check at every single
3464	 operation, which would be tedious, or we must do the computations
3465	 in a type larger than bfd_vma, which would be inefficient.  */
3466
3467      if ((unsigned int) howto.complain_on_overflow
3468	  >= XCOFF_MAX_COMPLAIN_OVERFLOW)
3469	abort ();
3470
3471      if (((*xcoff_complain_overflow[howto.complain_on_overflow])
3472	   (input_bfd, value_to_relocate, relocation, &howto)))
3473	{
3474	  const char *name;
3475	  char buf[SYMNMLEN + 1];
3476	  char reloc_type_name[10];
3477
3478	  if (symndx == -1)
3479	    {
3480	      name = "*ABS*";
3481	    }
3482	  else if (h != NULL)
3483	    {
3484	      name = h->root.root.string;
3485	    }
3486	  else
3487	    {
3488	      name = _bfd_coff_internal_syment_name (input_bfd, sym, buf);
3489	      if (name == NULL)
3490		name = "UNKNOWN";
3491	    }
3492	  sprintf (reloc_type_name, "0x%02x", rel->r_type);
3493
3494	  if (! ((*info->callbacks->reloc_overflow)
3495		 (info, name, reloc_type_name, (bfd_vma) 0, input_bfd,
3496		  input_section, rel->r_vaddr - input_section->vma)))
3497	    return FALSE;
3498	}
3499
3500      /* Add RELOCATION to the right bits of VALUE_TO_RELOCATE.  */
3501      value_to_relocate = ((value_to_relocate & ~howto.dst_mask)
3502			   | (((value_to_relocate & howto.src_mask)
3503			       + relocation) & howto.dst_mask));
3504
3505      /* Put the value back in the object file.  */
3506      if (1 == howto.size)
3507	bfd_put_16 (input_bfd, value_to_relocate, location);
3508      else
3509	bfd_put_32 (input_bfd, value_to_relocate, location);
3510    }
3511
3512  return TRUE;
3513}
3514
3515static bfd_boolean
3516_bfd_xcoff_put_ldsymbol_name (abfd, ldinfo, ldsym, name)
3517     bfd *abfd ATTRIBUTE_UNUSED;
3518	 struct xcoff_loader_info *ldinfo;
3519	 struct internal_ldsym *ldsym;
3520	 const char *name;
3521{
3522  size_t len;
3523  len = strlen (name);
3524
3525  if (len <= SYMNMLEN)
3526    strncpy (ldsym->_l._l_name, name, SYMNMLEN);
3527  else
3528    {
3529      if (ldinfo->string_size + len + 3 > ldinfo->string_alc)
3530	{
3531	  bfd_size_type newalc;
3532	  bfd_byte *newstrings;
3533
3534	  newalc = ldinfo->string_alc * 2;
3535	  if (newalc == 0)
3536	    newalc = 32;
3537	  while (ldinfo->string_size + len + 3 > newalc)
3538	    newalc *= 2;
3539
3540	  newstrings = ((bfd_byte *)
3541			bfd_realloc ((PTR) ldinfo->strings, newalc));
3542	  if (newstrings == NULL)
3543	    {
3544	      ldinfo->failed = TRUE;
3545	      return FALSE;
3546	    }
3547	  ldinfo->string_alc = newalc;
3548	  ldinfo->strings = newstrings;
3549	}
3550
3551      bfd_put_16 (ldinfo->output_bfd, (bfd_vma) (len + 1),
3552		  ldinfo->strings + ldinfo->string_size);
3553      strcpy (ldinfo->strings + ldinfo->string_size + 2, name);
3554      ldsym->_l._l_l._l_zeroes = 0;
3555      ldsym->_l._l_l._l_offset = ldinfo->string_size + 2;
3556      ldinfo->string_size += len + 3;
3557    }
3558
3559  return TRUE;
3560}
3561
3562static bfd_boolean
3563_bfd_xcoff_put_symbol_name (bfd *abfd, struct bfd_strtab_hash *strtab,
3564			    struct internal_syment *sym,
3565			    const char *name)
3566{
3567  if (strlen (name) <= SYMNMLEN)
3568    {
3569      strncpy (sym->_n._n_name, name, SYMNMLEN);
3570    }
3571  else
3572    {
3573      bfd_boolean hash;
3574      bfd_size_type indx;
3575
3576      hash = TRUE;
3577      if ((abfd->flags & BFD_TRADITIONAL_FORMAT) != 0)
3578	hash = FALSE;
3579      indx = _bfd_stringtab_add (strtab, name, hash, FALSE);
3580      if (indx == (bfd_size_type) -1)
3581	return FALSE;
3582      sym->_n._n_n._n_zeroes = 0;
3583      sym->_n._n_n._n_offset = STRING_SIZE_SIZE + indx;
3584    }
3585  return TRUE;
3586}
3587
3588static asection *
3589xcoff_create_csect_from_smclas (abfd, aux, symbol_name)
3590     bfd *abfd;
3591     union internal_auxent *aux;
3592     const char *symbol_name;
3593{
3594  asection *return_value = NULL;
3595
3596  /* .sv64 = x_smclas == 17
3597     This is an invalid csect for 32 bit apps.  */
3598  static const char *names[19] =
3599  {
3600    ".pr", ".ro", ".db", ".tc", ".ua", ".rw", ".gl", ".xo",
3601    ".sv", ".bs", ".ds", ".uc", ".ti", ".tb", NULL, ".tc0",
3602    ".td", NULL, ".sv3264"
3603  };
3604
3605  if ((19 >= aux->x_csect.x_smclas)
3606      && (NULL != names[aux->x_csect.x_smclas]))
3607    {
3608      return_value = bfd_make_section_anyway
3609	(abfd, names[aux->x_csect.x_smclas]);
3610    }
3611  else
3612    {
3613      (*_bfd_error_handler)
3614	(_("%B: symbol `%s' has unrecognized smclas %d"),
3615	 abfd, symbol_name, aux->x_csect.x_smclas);
3616      bfd_set_error (bfd_error_bad_value);
3617    }
3618
3619  return return_value;
3620}
3621
3622static bfd_boolean
3623xcoff_is_lineno_count_overflow (abfd, value)
3624    bfd *abfd ATTRIBUTE_UNUSED;
3625	bfd_vma value;
3626{
3627  if (0xffff <= value)
3628    return TRUE;
3629
3630  return FALSE;
3631}
3632
3633static bfd_boolean
3634xcoff_is_reloc_count_overflow (abfd, value)
3635    bfd *abfd ATTRIBUTE_UNUSED;
3636	bfd_vma value;
3637{
3638  if (0xffff <= value)
3639    return TRUE;
3640
3641  return FALSE;
3642}
3643
3644static bfd_vma
3645xcoff_loader_symbol_offset (abfd, ldhdr)
3646    bfd *abfd;
3647    struct internal_ldhdr *ldhdr ATTRIBUTE_UNUSED;
3648{
3649  return bfd_xcoff_ldhdrsz (abfd);
3650}
3651
3652static bfd_vma
3653xcoff_loader_reloc_offset (abfd, ldhdr)
3654    bfd *abfd;
3655    struct internal_ldhdr *ldhdr;
3656{
3657  return bfd_xcoff_ldhdrsz (abfd) + ldhdr->l_nsyms * bfd_xcoff_ldsymsz (abfd);
3658}
3659
3660static bfd_boolean
3661xcoff_generate_rtinit  (abfd, init, fini, rtld)
3662     bfd *abfd;
3663     const char *init;
3664     const char *fini;
3665     bfd_boolean rtld;
3666{
3667  bfd_byte filehdr_ext[FILHSZ];
3668  bfd_byte scnhdr_ext[SCNHSZ];
3669  bfd_byte syment_ext[SYMESZ * 10];
3670  bfd_byte reloc_ext[RELSZ * 3];
3671  bfd_byte *data_buffer;
3672  bfd_size_type data_buffer_size;
3673  bfd_byte *string_table = NULL, *st_tmp = NULL;
3674  bfd_size_type string_table_size;
3675  bfd_vma val;
3676  size_t initsz, finisz;
3677  struct internal_filehdr filehdr;
3678  struct internal_scnhdr scnhdr;
3679  struct internal_syment syment;
3680  union internal_auxent auxent;
3681  struct internal_reloc reloc;
3682
3683  char *data_name = ".data";
3684  char *rtinit_name = "__rtinit";
3685  char *rtld_name = "__rtld";
3686
3687  if (! bfd_xcoff_rtinit_size (abfd))
3688    return FALSE;
3689
3690  initsz = (init == NULL ? 0 : 1 + strlen (init));
3691  finisz = (fini == NULL ? 0 : 1 + strlen (fini));
3692
3693  /* file header */
3694  memset (filehdr_ext, 0, FILHSZ);
3695  memset (&filehdr, 0, sizeof (struct internal_filehdr));
3696  filehdr.f_magic = bfd_xcoff_magic_number (abfd);
3697  filehdr.f_nscns = 1;
3698  filehdr.f_timdat = 0;
3699  filehdr.f_nsyms = 0;  /* at least 6, no more than 10 */
3700  filehdr.f_symptr = 0; /* set below */
3701  filehdr.f_opthdr = 0;
3702  filehdr.f_flags = 0;
3703
3704  /* section header */
3705  memset (scnhdr_ext, 0, SCNHSZ);
3706  memset (&scnhdr, 0, sizeof (struct internal_scnhdr));
3707  memcpy (scnhdr.s_name, data_name, strlen (data_name));
3708  scnhdr.s_paddr = 0;
3709  scnhdr.s_vaddr = 0;
3710  scnhdr.s_size = 0;    /* set below */
3711  scnhdr.s_scnptr = FILHSZ + SCNHSZ;
3712  scnhdr.s_relptr = 0;  /* set below */
3713  scnhdr.s_lnnoptr = 0;
3714  scnhdr.s_nreloc = 0;  /* either 1 or 2 */
3715  scnhdr.s_nlnno = 0;
3716  scnhdr.s_flags = STYP_DATA;
3717
3718  /* .data
3719     0x0000	      0x00000000 : rtl
3720     0x0004	      0x00000010 : offset to init, or 0
3721     0x0008	      0x00000028 : offset to fini, or 0
3722     0x000C	      0x0000000C : size of descriptor
3723     0x0010	      0x00000000 : init, needs a reloc
3724     0x0014	      0x00000040 : offset to init name
3725     0x0018	      0x00000000 : flags, padded to a word
3726     0x001C	      0x00000000 : empty init
3727     0x0020	      0x00000000 :
3728     0x0024	      0x00000000 :
3729     0x0028	      0x00000000 : fini, needs a reloc
3730     0x002C	      0x00000??? : offset to fini name
3731     0x0030	      0x00000000 : flags, padded to a word
3732     0x0034	      0x00000000 : empty fini
3733     0x0038	      0x00000000 :
3734     0x003C	      0x00000000 :
3735     0x0040	      init name
3736     0x0040 + initsz  fini name */
3737
3738  data_buffer_size = 0x0040 + initsz + finisz;
3739  data_buffer_size = (data_buffer_size + 7) &~ (bfd_size_type) 7;
3740  data_buffer = NULL;
3741  data_buffer = (bfd_byte *) bfd_zmalloc (data_buffer_size);
3742  if (data_buffer == NULL)
3743    return FALSE;
3744
3745  if (initsz)
3746    {
3747      val = 0x10;
3748      bfd_h_put_32 (abfd, val, &data_buffer[0x04]);
3749      val = 0x40;
3750      bfd_h_put_32 (abfd, val, &data_buffer[0x14]);
3751      memcpy (&data_buffer[val], init, initsz);
3752    }
3753
3754  if (finisz)
3755    {
3756      val = 0x28;
3757      bfd_h_put_32 (abfd, val, &data_buffer[0x08]);
3758      val = 0x40 + initsz;
3759      bfd_h_put_32 (abfd, val, &data_buffer[0x2C]);
3760      memcpy (&data_buffer[val], fini, finisz);
3761    }
3762
3763  val = 0x0C;
3764  bfd_h_put_32 (abfd, val, &data_buffer[0x0C]);
3765
3766  scnhdr.s_size = data_buffer_size;
3767
3768  /* string table */
3769  string_table_size = 0;
3770  if (initsz > 9)
3771    string_table_size += initsz;
3772  if (finisz > 9)
3773    string_table_size += finisz;
3774  if (string_table_size)
3775    {
3776      string_table_size += 4;
3777      string_table = (bfd_byte *) bfd_zmalloc (string_table_size);
3778      if (string_table == NULL)
3779	return FALSE;
3780
3781      val = string_table_size;
3782      bfd_h_put_32 (abfd, val, &string_table[0]);
3783      st_tmp = string_table + 4;
3784    }
3785
3786  /* symbols
3787     0. .data csect
3788     2. __rtinit
3789     4. init function
3790     6. fini function
3791     8. __rtld  */
3792  memset (syment_ext, 0, 10 * SYMESZ);
3793  memset (reloc_ext, 0, 3 * RELSZ);
3794
3795  /* .data csect */
3796  memset (&syment, 0, sizeof (struct internal_syment));
3797  memset (&auxent, 0, sizeof (union internal_auxent));
3798  memcpy (syment._n._n_name, data_name, strlen (data_name));
3799  syment.n_scnum = 1;
3800  syment.n_sclass = C_HIDEXT;
3801  syment.n_numaux = 1;
3802  auxent.x_csect.x_scnlen.l = data_buffer_size;
3803  auxent.x_csect.x_smtyp = 3 << 3 | XTY_SD;
3804  auxent.x_csect.x_smclas = XMC_RW;
3805  bfd_coff_swap_sym_out (abfd, &syment,
3806			 &syment_ext[filehdr.f_nsyms * SYMESZ]);
3807  bfd_coff_swap_aux_out (abfd, &auxent, syment.n_type, syment.n_sclass, 0,
3808			 syment.n_numaux,
3809			 &syment_ext[(filehdr.f_nsyms + 1) * SYMESZ]);
3810  filehdr.f_nsyms += 2;
3811
3812  /* __rtinit */
3813  memset (&syment, 0, sizeof (struct internal_syment));
3814  memset (&auxent, 0, sizeof (union internal_auxent));
3815  memcpy (syment._n._n_name, rtinit_name, strlen (rtinit_name));
3816  syment.n_scnum = 1;
3817  syment.n_sclass = C_EXT;
3818  syment.n_numaux = 1;
3819  auxent.x_csect.x_smtyp = XTY_LD;
3820  auxent.x_csect.x_smclas = XMC_RW;
3821  bfd_coff_swap_sym_out (abfd, &syment,
3822			 &syment_ext[filehdr.f_nsyms * SYMESZ]);
3823  bfd_coff_swap_aux_out (abfd, &auxent, syment.n_type, syment.n_sclass, 0,
3824			 syment.n_numaux,
3825			 &syment_ext[(filehdr.f_nsyms + 1) * SYMESZ]);
3826  filehdr.f_nsyms += 2;
3827
3828  /* init */
3829  if (initsz)
3830    {
3831      memset (&syment, 0, sizeof (struct internal_syment));
3832      memset (&auxent, 0, sizeof (union internal_auxent));
3833
3834      if (initsz > 9)
3835	{
3836	  syment._n._n_n._n_offset = st_tmp - string_table;
3837	  memcpy (st_tmp, init, initsz);
3838	  st_tmp += initsz;
3839	}
3840      else
3841	memcpy (syment._n._n_name, init, initsz - 1);
3842
3843      syment.n_sclass = C_EXT;
3844      syment.n_numaux = 1;
3845      bfd_coff_swap_sym_out (abfd, &syment,
3846			     &syment_ext[filehdr.f_nsyms * SYMESZ]);
3847      bfd_coff_swap_aux_out (abfd, &auxent, syment.n_type, syment.n_sclass, 0,
3848			     syment.n_numaux,
3849			     &syment_ext[(filehdr.f_nsyms + 1) * SYMESZ]);
3850
3851      /* reloc */
3852      memset (&reloc, 0, sizeof (struct internal_reloc));
3853      reloc.r_vaddr = 0x0010;
3854      reloc.r_symndx = filehdr.f_nsyms;
3855      reloc.r_type = R_POS;
3856      reloc.r_size = 31;
3857      bfd_coff_swap_reloc_out (abfd, &reloc, &reloc_ext[0]);
3858
3859      filehdr.f_nsyms += 2;
3860      scnhdr.s_nreloc += 1;
3861    }
3862
3863  /* fini */
3864  if (finisz)
3865    {
3866      memset (&syment, 0, sizeof (struct internal_syment));
3867      memset (&auxent, 0, sizeof (union internal_auxent));
3868
3869      if (finisz > 9)
3870	{
3871	  syment._n._n_n._n_offset = st_tmp - string_table;
3872	  memcpy (st_tmp, fini, finisz);
3873	  st_tmp += finisz;
3874	}
3875      else
3876	memcpy (syment._n._n_name, fini, finisz - 1);
3877
3878      syment.n_sclass = C_EXT;
3879      syment.n_numaux = 1;
3880      bfd_coff_swap_sym_out (abfd, &syment,
3881			     &syment_ext[filehdr.f_nsyms * SYMESZ]);
3882      bfd_coff_swap_aux_out (abfd, &auxent, syment.n_type, syment.n_sclass, 0,
3883			     syment.n_numaux,
3884			     &syment_ext[(filehdr.f_nsyms + 1) * SYMESZ]);
3885
3886      /* reloc */
3887      memset (&reloc, 0, sizeof (struct internal_reloc));
3888      reloc.r_vaddr = 0x0028;
3889      reloc.r_symndx = filehdr.f_nsyms;
3890      reloc.r_type = R_POS;
3891      reloc.r_size = 31;
3892      bfd_coff_swap_reloc_out (abfd, &reloc,
3893			       &reloc_ext[scnhdr.s_nreloc * RELSZ]);
3894
3895      filehdr.f_nsyms += 2;
3896      scnhdr.s_nreloc += 1;
3897    }
3898
3899  if (rtld)
3900    {
3901      memset (&syment, 0, sizeof (struct internal_syment));
3902      memset (&auxent, 0, sizeof (union internal_auxent));
3903      memcpy (syment._n._n_name, rtld_name, strlen (rtld_name));
3904      syment.n_sclass = C_EXT;
3905      syment.n_numaux = 1;
3906      bfd_coff_swap_sym_out (abfd, &syment,
3907			     &syment_ext[filehdr.f_nsyms * SYMESZ]);
3908      bfd_coff_swap_aux_out (abfd, &auxent, syment.n_type, syment.n_sclass, 0,
3909			     syment.n_numaux,
3910			     &syment_ext[(filehdr.f_nsyms + 1) * SYMESZ]);
3911
3912      /* reloc */
3913      memset (&reloc, 0, sizeof (struct internal_reloc));
3914      reloc.r_vaddr = 0x0000;
3915      reloc.r_symndx = filehdr.f_nsyms;
3916      reloc.r_type = R_POS;
3917      reloc.r_size = 31;
3918      bfd_coff_swap_reloc_out (abfd, &reloc,
3919			       &reloc_ext[scnhdr.s_nreloc * RELSZ]);
3920
3921      filehdr.f_nsyms += 2;
3922      scnhdr.s_nreloc += 1;
3923    }
3924
3925  scnhdr.s_relptr = scnhdr.s_scnptr + data_buffer_size;
3926  filehdr.f_symptr = scnhdr.s_relptr + scnhdr.s_nreloc * RELSZ;
3927
3928  bfd_coff_swap_filehdr_out (abfd, &filehdr, filehdr_ext);
3929  bfd_bwrite (filehdr_ext, FILHSZ, abfd);
3930  bfd_coff_swap_scnhdr_out (abfd, &scnhdr, scnhdr_ext);
3931  bfd_bwrite (scnhdr_ext, SCNHSZ, abfd);
3932  bfd_bwrite (data_buffer, data_buffer_size, abfd);
3933  bfd_bwrite (reloc_ext, scnhdr.s_nreloc * RELSZ, abfd);
3934  bfd_bwrite (syment_ext, filehdr.f_nsyms * SYMESZ, abfd);
3935  bfd_bwrite (string_table, string_table_size, abfd);
3936
3937  free (data_buffer);
3938  data_buffer = NULL;
3939
3940  return TRUE;
3941}
3942
3943
3944static reloc_howto_type xcoff_dynamic_reloc =
3945HOWTO (0,			/* type */
3946       0,			/* rightshift */
3947       2,			/* size (0 = byte, 1 = short, 2 = long) */
3948       32,			/* bitsize */
3949       FALSE,			/* pc_relative */
3950       0,			/* bitpos */
3951       complain_overflow_bitfield, /* complain_on_overflow */
3952       0,			/* special_function */
3953       "R_POS",			/* name */
3954       TRUE,			/* partial_inplace */
3955       0xffffffff,		/* src_mask */
3956       0xffffffff,		/* dst_mask */
3957       FALSE);			/* pcrel_offset */
3958
3959/*  glink
3960
3961   The first word of global linkage code must be modified by filling in
3962   the correct TOC offset.  */
3963
3964static unsigned long xcoff_glink_code[9] =
3965  {
3966    0x81820000,	/* lwz r12,0(r2) */
3967    0x90410014,	/* stw r2,20(r1) */
3968    0x800c0000,	/* lwz r0,0(r12) */
3969    0x804c0004,	/* lwz r2,4(r12) */
3970    0x7c0903a6,	/* mtctr r0 */
3971    0x4e800420,	/* bctr */
3972    0x00000000,	/* start of traceback table */
3973    0x000c8000,	/* traceback table */
3974    0x00000000,	/* traceback table */
3975  };
3976
3977
3978static const struct xcoff_backend_data_rec bfd_xcoff_backend_data =
3979  {
3980    { /* COFF backend, defined in libcoff.h.  */
3981      _bfd_xcoff_swap_aux_in,
3982      _bfd_xcoff_swap_sym_in,
3983      coff_swap_lineno_in,
3984      _bfd_xcoff_swap_aux_out,
3985      _bfd_xcoff_swap_sym_out,
3986      coff_swap_lineno_out,
3987      xcoff_swap_reloc_out,
3988      coff_swap_filehdr_out,
3989      coff_swap_aouthdr_out,
3990      coff_swap_scnhdr_out,
3991      FILHSZ,
3992      AOUTSZ,
3993      SCNHSZ,
3994      SYMESZ,
3995      AUXESZ,
3996      RELSZ,
3997      LINESZ,
3998      FILNMLEN,
3999      TRUE,			/* _bfd_coff_long_filenames */
4000      FALSE,			/* _bfd_coff_long_section_names */
4001      3,			/* _bfd_coff_default_section_alignment_power */
4002      FALSE,			/* _bfd_coff_force_symnames_in_strings */
4003      2,			/* _bfd_coff_debug_string_prefix_length */
4004      coff_swap_filehdr_in,
4005      coff_swap_aouthdr_in,
4006      coff_swap_scnhdr_in,
4007      xcoff_swap_reloc_in,
4008      coff_bad_format_hook,
4009      coff_set_arch_mach_hook,
4010      coff_mkobject_hook,
4011      styp_to_sec_flags,
4012      coff_set_alignment_hook,
4013      coff_slurp_symbol_table,
4014      symname_in_debug_hook,
4015      coff_pointerize_aux_hook,
4016      coff_print_aux,
4017      dummy_reloc16_extra_cases,
4018      dummy_reloc16_estimate,
4019      NULL,			/* bfd_coff_sym_is_global */
4020      coff_compute_section_file_positions,
4021      NULL,			/* _bfd_coff_start_final_link */
4022      xcoff_ppc_relocate_section,
4023      coff_rtype_to_howto,
4024      NULL,			/* _bfd_coff_adjust_symndx */
4025      _bfd_generic_link_add_one_symbol,
4026      coff_link_output_has_begun,
4027      coff_final_link_postscript
4028    },
4029
4030    0x01DF,			/* magic number */
4031    bfd_arch_rs6000,
4032    bfd_mach_rs6k,
4033
4034    /* Function pointers to xcoff specific swap routines.  */
4035    xcoff_swap_ldhdr_in,
4036    xcoff_swap_ldhdr_out,
4037    xcoff_swap_ldsym_in,
4038    xcoff_swap_ldsym_out,
4039    xcoff_swap_ldrel_in,
4040    xcoff_swap_ldrel_out,
4041
4042    /* Sizes.  */
4043    LDHDRSZ,
4044    LDSYMSZ,
4045    LDRELSZ,
4046    12,				/* _xcoff_function_descriptor_size */
4047    SMALL_AOUTSZ,
4048
4049    /* Versions.  */
4050    1,				/* _xcoff_ldhdr_version */
4051
4052    _bfd_xcoff_put_symbol_name,
4053    _bfd_xcoff_put_ldsymbol_name,
4054    &xcoff_dynamic_reloc,
4055    xcoff_create_csect_from_smclas,
4056
4057    /* Lineno and reloc count overflow.  */
4058    xcoff_is_lineno_count_overflow,
4059    xcoff_is_reloc_count_overflow,
4060
4061    xcoff_loader_symbol_offset,
4062    xcoff_loader_reloc_offset,
4063
4064    /* glink.  */
4065    &xcoff_glink_code[0],
4066    36,				/* _xcoff_glink_size */
4067
4068    /* rtinit */
4069    64,				/* _xcoff_rtinit_size */
4070    xcoff_generate_rtinit,
4071  };
4072
4073/* The transfer vector that leads the outside world to all of the above.  */
4074const bfd_target rs6000coff_vec =
4075  {
4076    "aixcoff-rs6000",
4077    bfd_target_xcoff_flavour,
4078    BFD_ENDIAN_BIG,		/* data byte order is big */
4079    BFD_ENDIAN_BIG,		/* header byte order is big */
4080
4081    (HAS_RELOC | EXEC_P | HAS_LINENO | HAS_DEBUG | DYNAMIC
4082     | HAS_SYMS | HAS_LOCALS | WP_TEXT),
4083
4084    SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_RELOC | SEC_CODE | SEC_DATA,
4085    0,				/* leading char */
4086    '/',			/* ar_pad_char */
4087    15,				/* ar_max_namelen */
4088
4089    /* data */
4090    bfd_getb64,
4091    bfd_getb_signed_64,
4092    bfd_putb64,
4093    bfd_getb32,
4094    bfd_getb_signed_32,
4095    bfd_putb32,
4096    bfd_getb16,
4097    bfd_getb_signed_16,
4098    bfd_putb16,
4099
4100    /* hdrs */
4101    bfd_getb64,
4102    bfd_getb_signed_64,
4103    bfd_putb64,
4104    bfd_getb32,
4105    bfd_getb_signed_32,
4106    bfd_putb32,
4107    bfd_getb16,
4108    bfd_getb_signed_16,
4109    bfd_putb16,
4110
4111    { /* bfd_check_format */
4112      _bfd_dummy_target,
4113      coff_object_p,
4114      _bfd_xcoff_archive_p,
4115      CORE_FILE_P
4116    },
4117
4118    { /* bfd_set_format */
4119      bfd_false,
4120      coff_mkobject,
4121      _bfd_generic_mkarchive,
4122      bfd_false
4123    },
4124
4125    {/* bfd_write_contents */
4126      bfd_false,
4127      coff_write_object_contents,
4128      _bfd_xcoff_write_archive_contents,
4129      bfd_false
4130    },
4131
4132    /* Generic */
4133    bfd_true,
4134    bfd_true,
4135    coff_new_section_hook,
4136    _bfd_generic_get_section_contents,
4137    _bfd_generic_get_section_contents_in_window,
4138
4139    /* Copy */
4140    _bfd_xcoff_copy_private_bfd_data,
4141    ((bfd_boolean (*) (bfd *, bfd *)) bfd_true),
4142    ((bfd_boolean (*) (bfd *, asection *, bfd *, asection *)) bfd_true),
4143    ((bfd_boolean (*) (bfd *, asymbol *, bfd *, asymbol *)) bfd_true),
4144    ((bfd_boolean (*) (bfd *, bfd *)) bfd_true),
4145    ((bfd_boolean (*) (bfd *, flagword)) bfd_true),
4146    ((bfd_boolean (*) (bfd *, void * )) bfd_true),
4147
4148    /* Core */
4149    coff_core_file_failing_command,
4150    coff_core_file_failing_signal,
4151    coff_core_file_matches_executable_p,
4152
4153    /* Archive */
4154    _bfd_xcoff_slurp_armap,
4155    bfd_false,
4156    ((bfd_boolean (*) (bfd *, char **, bfd_size_type *, const char **)) bfd_false),
4157    bfd_dont_truncate_arname,
4158    _bfd_xcoff_write_armap,
4159    _bfd_xcoff_read_ar_hdr,
4160    _bfd_xcoff_openr_next_archived_file,
4161    _bfd_generic_get_elt_at_index,
4162    _bfd_xcoff_stat_arch_elt,
4163    bfd_true,
4164
4165    /* Symbols */
4166    coff_get_symtab_upper_bound,
4167    coff_canonicalize_symtab,
4168    coff_make_empty_symbol,
4169    coff_print_symbol,
4170    coff_get_symbol_info,
4171    _bfd_xcoff_is_local_label_name,
4172    coff_bfd_is_target_special_symbol,
4173    coff_get_lineno,
4174    coff_find_nearest_line,
4175    coff_bfd_make_debug_symbol,
4176    _bfd_generic_read_minisymbols,
4177    _bfd_generic_minisymbol_to_symbol,
4178
4179    /* Reloc */
4180    coff_get_reloc_upper_bound,
4181    coff_canonicalize_reloc,
4182    _bfd_xcoff_reloc_type_lookup,
4183
4184    /* Write */
4185    coff_set_arch_mach,
4186    coff_set_section_contents,
4187
4188    /* Link */
4189    _bfd_xcoff_sizeof_headers,
4190    bfd_generic_get_relocated_section_contents,
4191    bfd_generic_relax_section,
4192    _bfd_xcoff_bfd_link_hash_table_create,
4193    _bfd_generic_link_hash_table_free,
4194    _bfd_xcoff_bfd_link_add_symbols,
4195    _bfd_generic_link_just_syms,
4196    _bfd_xcoff_bfd_final_link,
4197    _bfd_generic_link_split_section,
4198    bfd_generic_gc_sections,
4199    bfd_generic_merge_sections,
4200    bfd_generic_is_group_section,
4201    bfd_generic_discard_group,
4202    _bfd_generic_section_already_linked,
4203
4204    /* Dynamic */
4205    _bfd_xcoff_get_dynamic_symtab_upper_bound,
4206    _bfd_xcoff_canonicalize_dynamic_symtab,
4207    _bfd_nodynamic_get_synthetic_symtab,
4208    _bfd_xcoff_get_dynamic_reloc_upper_bound,
4209    _bfd_xcoff_canonicalize_dynamic_reloc,
4210
4211    /* Opposite endian version, none exists */
4212    NULL,
4213
4214    (void *) &bfd_xcoff_backend_data,
4215  };
4216
4217/* xcoff-powermac target
4218   Old target.
4219   Only difference between this target and the rs6000 target is the
4220   the default architecture and machine type used in coffcode.h
4221
4222   PowerPC Macs use the same magic numbers as RS/6000
4223   (because that's how they were bootstrapped originally),
4224   but they are always PowerPC architecture.  */
4225static const struct xcoff_backend_data_rec bfd_pmac_xcoff_backend_data =
4226  {
4227    { /* COFF backend, defined in libcoff.h.  */
4228      _bfd_xcoff_swap_aux_in,
4229      _bfd_xcoff_swap_sym_in,
4230      coff_swap_lineno_in,
4231      _bfd_xcoff_swap_aux_out,
4232      _bfd_xcoff_swap_sym_out,
4233      coff_swap_lineno_out,
4234      xcoff_swap_reloc_out,
4235      coff_swap_filehdr_out,
4236      coff_swap_aouthdr_out,
4237      coff_swap_scnhdr_out,
4238      FILHSZ,
4239      AOUTSZ,
4240      SCNHSZ,
4241      SYMESZ,
4242      AUXESZ,
4243      RELSZ,
4244      LINESZ,
4245      FILNMLEN,
4246      TRUE,			/* _bfd_coff_long_filenames */
4247      FALSE,			/* _bfd_coff_long_section_names */
4248      3,			/* _bfd_coff_default_section_alignment_power */
4249      FALSE,			/* _bfd_coff_force_symnames_in_strings */
4250      2,			/* _bfd_coff_debug_string_prefix_length */
4251      coff_swap_filehdr_in,
4252      coff_swap_aouthdr_in,
4253      coff_swap_scnhdr_in,
4254      xcoff_swap_reloc_in,
4255      coff_bad_format_hook,
4256      coff_set_arch_mach_hook,
4257      coff_mkobject_hook,
4258      styp_to_sec_flags,
4259      coff_set_alignment_hook,
4260      coff_slurp_symbol_table,
4261      symname_in_debug_hook,
4262      coff_pointerize_aux_hook,
4263      coff_print_aux,
4264      dummy_reloc16_extra_cases,
4265      dummy_reloc16_estimate,
4266      NULL,			/* bfd_coff_sym_is_global */
4267      coff_compute_section_file_positions,
4268      NULL,			/* _bfd_coff_start_final_link */
4269      xcoff_ppc_relocate_section,
4270      coff_rtype_to_howto,
4271      NULL,			/* _bfd_coff_adjust_symndx */
4272      _bfd_generic_link_add_one_symbol,
4273      coff_link_output_has_begun,
4274      coff_final_link_postscript
4275    },
4276
4277    0x01DF,			/* magic number */
4278    bfd_arch_powerpc,
4279    bfd_mach_ppc,
4280
4281    /* Function pointers to xcoff specific swap routines.  */
4282    xcoff_swap_ldhdr_in,
4283    xcoff_swap_ldhdr_out,
4284    xcoff_swap_ldsym_in,
4285    xcoff_swap_ldsym_out,
4286    xcoff_swap_ldrel_in,
4287    xcoff_swap_ldrel_out,
4288
4289    /* Sizes.  */
4290    LDHDRSZ,
4291    LDSYMSZ,
4292    LDRELSZ,
4293    12,				/* _xcoff_function_descriptor_size */
4294    SMALL_AOUTSZ,
4295
4296    /* Versions.  */
4297    1,				/* _xcoff_ldhdr_version */
4298
4299    _bfd_xcoff_put_symbol_name,
4300    _bfd_xcoff_put_ldsymbol_name,
4301    &xcoff_dynamic_reloc,
4302    xcoff_create_csect_from_smclas,
4303
4304    /* Lineno and reloc count overflow.  */
4305    xcoff_is_lineno_count_overflow,
4306    xcoff_is_reloc_count_overflow,
4307
4308    xcoff_loader_symbol_offset,
4309    xcoff_loader_reloc_offset,
4310
4311    /* glink.  */
4312    &xcoff_glink_code[0],
4313    36,				/* _xcoff_glink_size */
4314
4315    /* rtinit */
4316    0,				/* _xcoff_rtinit_size */
4317    xcoff_generate_rtinit,
4318  };
4319
4320/* The transfer vector that leads the outside world to all of the above.  */
4321const bfd_target pmac_xcoff_vec =
4322  {
4323    "xcoff-powermac",
4324    bfd_target_xcoff_flavour,
4325    BFD_ENDIAN_BIG,		/* data byte order is big */
4326    BFD_ENDIAN_BIG,		/* header byte order is big */
4327
4328    (HAS_RELOC | EXEC_P | HAS_LINENO | HAS_DEBUG | DYNAMIC
4329     | HAS_SYMS | HAS_LOCALS | WP_TEXT),
4330
4331    SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD | SEC_RELOC | SEC_CODE | SEC_DATA,
4332    0,				/* leading char */
4333    '/',			/* ar_pad_char */
4334    15,				/* ar_max_namelen */
4335
4336    /* data */
4337    bfd_getb64,
4338    bfd_getb_signed_64,
4339    bfd_putb64,
4340    bfd_getb32,
4341    bfd_getb_signed_32,
4342    bfd_putb32,
4343    bfd_getb16,
4344    bfd_getb_signed_16,
4345    bfd_putb16,
4346
4347    /* hdrs */
4348    bfd_getb64,
4349    bfd_getb_signed_64,
4350    bfd_putb64,
4351    bfd_getb32,
4352    bfd_getb_signed_32,
4353    bfd_putb32,
4354    bfd_getb16,
4355    bfd_getb_signed_16,
4356    bfd_putb16,
4357
4358    { /* bfd_check_format */
4359      _bfd_dummy_target,
4360      coff_object_p,
4361      _bfd_xcoff_archive_p,
4362      CORE_FILE_P
4363    },
4364
4365    { /* bfd_set_format */
4366      bfd_false,
4367      coff_mkobject,
4368      _bfd_generic_mkarchive,
4369      bfd_false
4370    },
4371
4372    {/* bfd_write_contents */
4373      bfd_false,
4374      coff_write_object_contents,
4375      _bfd_xcoff_write_archive_contents,
4376      bfd_false
4377    },
4378
4379    /* Generic */
4380    bfd_true,
4381    bfd_true,
4382    coff_new_section_hook,
4383    _bfd_generic_get_section_contents,
4384    _bfd_generic_get_section_contents_in_window,
4385
4386    /* Copy */
4387    _bfd_xcoff_copy_private_bfd_data,
4388    ((bfd_boolean (*) (bfd *, bfd *)) bfd_true),
4389    ((bfd_boolean (*) (bfd *, asection *, bfd *, asection *)) bfd_true),
4390    ((bfd_boolean (*) (bfd *, asymbol *, bfd *, asymbol *)) bfd_true),
4391    ((bfd_boolean (*) (bfd *, bfd *)) bfd_true),
4392    ((bfd_boolean (*) (bfd *, flagword)) bfd_true),
4393    ((bfd_boolean (*) (bfd *, void * )) bfd_true),
4394
4395    /* Core */
4396    coff_core_file_failing_command,
4397    coff_core_file_failing_signal,
4398    coff_core_file_matches_executable_p,
4399
4400    /* Archive */
4401    _bfd_xcoff_slurp_armap,
4402    bfd_false,
4403    ((bfd_boolean (*) (bfd *, char **, bfd_size_type *, const char **)) bfd_false),
4404    bfd_dont_truncate_arname,
4405    _bfd_xcoff_write_armap,
4406    _bfd_xcoff_read_ar_hdr,
4407    _bfd_xcoff_openr_next_archived_file,
4408    _bfd_generic_get_elt_at_index,
4409    _bfd_xcoff_stat_arch_elt,
4410    bfd_true,
4411
4412    /* Symbols */
4413    coff_get_symtab_upper_bound,
4414    coff_canonicalize_symtab,
4415    coff_make_empty_symbol,
4416    coff_print_symbol,
4417    coff_get_symbol_info,
4418    _bfd_xcoff_is_local_label_name,
4419    coff_bfd_is_target_special_symbol,
4420    coff_get_lineno,
4421    coff_find_nearest_line,
4422    coff_bfd_make_debug_symbol,
4423    _bfd_generic_read_minisymbols,
4424    _bfd_generic_minisymbol_to_symbol,
4425
4426    /* Reloc */
4427    coff_get_reloc_upper_bound,
4428    coff_canonicalize_reloc,
4429    _bfd_xcoff_reloc_type_lookup,
4430
4431    /* Write */
4432    coff_set_arch_mach,
4433    coff_set_section_contents,
4434
4435    /* Link */
4436    _bfd_xcoff_sizeof_headers,
4437    bfd_generic_get_relocated_section_contents,
4438    bfd_generic_relax_section,
4439    _bfd_xcoff_bfd_link_hash_table_create,
4440    _bfd_generic_link_hash_table_free,
4441    _bfd_xcoff_bfd_link_add_symbols,
4442    _bfd_generic_link_just_syms,
4443    _bfd_xcoff_bfd_final_link,
4444    _bfd_generic_link_split_section,
4445    bfd_generic_gc_sections,
4446    bfd_generic_merge_sections,
4447    bfd_generic_is_group_section,
4448    bfd_generic_discard_group,
4449    _bfd_generic_section_already_linked,
4450
4451    /* Dynamic */
4452    _bfd_xcoff_get_dynamic_symtab_upper_bound,
4453    _bfd_xcoff_canonicalize_dynamic_symtab,
4454    _bfd_nodynamic_get_synthetic_symtab,
4455    _bfd_xcoff_get_dynamic_reloc_upper_bound,
4456    _bfd_xcoff_canonicalize_dynamic_reloc,
4457
4458    /* Opposite endian version, none exists */
4459    NULL,
4460
4461    (void *) &bfd_pmac_xcoff_backend_data,
4462  };
4463