Back to index

cell-binutils  2.17cvs20070401
ecoff.c
Go to the documentation of this file.
00001 /* Generic ECOFF (Extended-COFF) routines.
00002    Copyright 1990, 1991, 1993, 1994, 1995, 1996, 1998, 1999, 2000, 2001,
00003    2002, 2003, 2004, 2005, 2006 Free Software Foundation, Inc.
00004    Original version by Per Bothner.
00005    Full support added by Ian Lance Taylor, ian@cygnus.com.
00006 
00007    This file is part of BFD, the Binary File Descriptor library.
00008 
00009    This program is free software; you can redistribute it and/or modify
00010    it under the terms of the GNU General Public License as published by
00011    the Free Software Foundation; either version 2 of the License, or
00012    (at your option) any later version.
00013 
00014    This program is distributed in the hope that it will be useful,
00015    but WITHOUT ANY WARRANTY; without even the implied warranty of
00016    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00017    GNU General Public License for more details.
00018 
00019    You should have received a copy of the GNU General Public License
00020    along with this program; if not, write to the Free Software
00021    Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA.  */
00022 
00023 #include "bfd.h"
00024 #include "sysdep.h"
00025 #include "bfdlink.h"
00026 #include "libbfd.h"
00027 #include "aout/ar.h"
00028 #include "aout/ranlib.h"
00029 #include "aout/stab_gnu.h"
00030 
00031 /* FIXME: We need the definitions of N_SET[ADTB], but aout64.h defines
00032    some other stuff which we don't want and which conflicts with stuff
00033    we do want.  */
00034 #include "libaout.h"
00035 #include "aout/aout64.h"
00036 #undef N_ABS
00037 #undef exec_hdr
00038 #undef obj_sym_filepos
00039 
00040 #include "coff/internal.h"
00041 #include "coff/sym.h"
00042 #include "coff/symconst.h"
00043 #include "coff/ecoff.h"
00044 #include "libcoff.h"
00045 #include "libecoff.h"
00046 #include "libiberty.h"
00047 
00048 #define streq(a, b)  (strcmp ((a), (b)) == 0)
00049 #define strneq(a, b, n)     (strncmp ((a), (b), (n)) == 0)
00050 
00051 
00052 /* This stuff is somewhat copied from coffcode.h.  */
00053 static asection bfd_debug_section =
00054 {
00055   /* name,      id,  index, next, prev, flags, user_set_vma,       */
00056      "*DEBUG*", 0,   0,     NULL, NULL, 0,     0,
00057   /* linker_mark, linker_has_input, gc_mark, gc_mark_from_eh,      */
00058      0,           0,                1,       0,
00059   /* segment_mark, sec_info_type, use_rela_p, has_tls_reloc,       */
00060      0,            0,             0,          0,
00061   /* has_gp_reloc, need_finalize_relax, reloc_done,                */
00062      0,            0,                   0,
00063   /* vma, lma, size, rawsize,                                      */
00064      0,   0,   0,    0,
00065   /* output_offset, output_section, alignment_power,               */
00066      0,             NULL,           0,
00067   /* relocation, orelocation, reloc_count, filepos, rel_filepos,   */
00068      NULL,       NULL,        0,           0,       0,
00069   /* line_filepos, userdata, contents, lineno, lineno_count,       */
00070      0,            NULL,     NULL,     NULL,   0,
00071   /* entsize, kept_section, moving_line_filepos,                   */
00072      0,       NULL,         0,
00073   /* target_index, used_by_bfd, constructor_chain, owner,          */
00074      0,            NULL,        NULL,              NULL,
00075   /* symbol,                                                       */
00076      NULL,
00077   /* symbol_ptr_ptr,                                               */
00078      NULL,
00079   /* map_head, map_tail                                            */
00080      { NULL }, { NULL }
00081 };
00082 
00083 /* Create an ECOFF object.  */
00084 
00085 bfd_boolean
00086 _bfd_ecoff_mkobject (bfd *abfd)
00087 {
00088   bfd_size_type amt = sizeof (ecoff_data_type);
00089 
00090   abfd->tdata.ecoff_obj_data = bfd_zalloc (abfd, amt);
00091   if (abfd->tdata.ecoff_obj_data == NULL)
00092     return FALSE;
00093 
00094   return TRUE;
00095 }
00096 
00097 /* This is a hook called by coff_real_object_p to create any backend
00098    specific information.  */
00099 
00100 void *
00101 _bfd_ecoff_mkobject_hook (bfd *abfd, void * filehdr, void * aouthdr)
00102 {
00103   struct internal_filehdr *internal_f = (struct internal_filehdr *) filehdr;
00104   struct internal_aouthdr *internal_a = (struct internal_aouthdr *) aouthdr;
00105   ecoff_data_type *ecoff;
00106 
00107   if (! _bfd_ecoff_mkobject (abfd))
00108     return NULL;
00109 
00110   ecoff = ecoff_data (abfd);
00111   ecoff->gp_size = 8;
00112   ecoff->sym_filepos = internal_f->f_symptr;
00113 
00114   if (internal_a != NULL)
00115     {
00116       int i;
00117 
00118       ecoff->text_start = internal_a->text_start;
00119       ecoff->text_end = internal_a->text_start + internal_a->tsize;
00120       ecoff->gp = internal_a->gp_value;
00121       ecoff->gprmask = internal_a->gprmask;
00122       for (i = 0; i < 4; i++)
00123        ecoff->cprmask[i] = internal_a->cprmask[i];
00124       ecoff->fprmask = internal_a->fprmask;
00125       if (internal_a->magic == ECOFF_AOUT_ZMAGIC)
00126        abfd->flags |= D_PAGED;
00127       else
00128        abfd->flags &=~ D_PAGED;
00129     }
00130 
00131   /* It turns out that no special action is required by the MIPS or
00132      Alpha ECOFF backends.  They have different information in the
00133      a.out header, but we just copy it all (e.g., gprmask, cprmask and
00134      fprmask) and let the swapping routines ensure that only relevant
00135      information is written out.  */
00136 
00137   return (void *) ecoff;
00138 }
00139 
00140 /* Initialize a new section.  */
00141 
00142 bfd_boolean
00143 _bfd_ecoff_new_section_hook (bfd *abfd, asection *section)
00144 {
00145   unsigned int i;
00146   static struct
00147   {
00148     const char * name;
00149     flagword flags;
00150   }
00151   section_flags [] =
00152   {
00153     { _TEXT,   SEC_ALLOC | SEC_CODE | SEC_LOAD },
00154     { _INIT,   SEC_ALLOC | SEC_CODE | SEC_LOAD },
00155     { _FINI,   SEC_ALLOC | SEC_CODE | SEC_LOAD },
00156     { _DATA,   SEC_ALLOC | SEC_DATA | SEC_LOAD },
00157     { _SDATA,  SEC_ALLOC | SEC_DATA | SEC_LOAD },
00158     { _RDATA,  SEC_ALLOC | SEC_DATA | SEC_LOAD | SEC_READONLY},
00159     { _LIT8,   SEC_ALLOC | SEC_DATA | SEC_LOAD | SEC_READONLY},
00160     { _LIT4,   SEC_ALLOC | SEC_DATA | SEC_LOAD | SEC_READONLY},
00161     { _RCONST, SEC_ALLOC | SEC_DATA | SEC_LOAD | SEC_READONLY},
00162     { _PDATA,  SEC_ALLOC | SEC_DATA | SEC_LOAD | SEC_READONLY},
00163     { _BSS,    SEC_ALLOC},
00164     { _SBSS,   SEC_ALLOC},
00165     /* An Irix 4 shared libary.  */
00166     { _LIB,    SEC_COFF_SHARED_LIBRARY}
00167   };
00168 
00169   section->alignment_power = 4;
00170 
00171   for (i = 0; i < ARRAY_SIZE (section_flags); i++)
00172     if (streq (section->name, section_flags[i].name))
00173       {
00174        section->flags |= section_flags[i].flags;
00175        break;
00176       }
00177 
00178 
00179   /* Probably any other section name is SEC_NEVER_LOAD, but I'm
00180      uncertain about .init on some systems and I don't know how shared
00181      libraries work.  */
00182 
00183   return _bfd_generic_new_section_hook (abfd, section);
00184 }
00185 
00186 /* Determine the machine architecture and type.  This is called from
00187    the generic COFF routines.  It is the inverse of ecoff_get_magic,
00188    below.  This could be an ECOFF backend routine, with one version
00189    for each target, but there aren't all that many ECOFF targets.  */
00190 
00191 bfd_boolean
00192 _bfd_ecoff_set_arch_mach_hook (bfd *abfd, void * filehdr)
00193 {
00194   struct internal_filehdr *internal_f = filehdr;
00195   enum bfd_architecture arch;
00196   unsigned long mach;
00197 
00198   switch (internal_f->f_magic)
00199     {
00200     case MIPS_MAGIC_1:
00201     case MIPS_MAGIC_LITTLE:
00202     case MIPS_MAGIC_BIG:
00203       arch = bfd_arch_mips;
00204       mach = bfd_mach_mips3000;
00205       break;
00206 
00207     case MIPS_MAGIC_LITTLE2:
00208     case MIPS_MAGIC_BIG2:
00209       /* MIPS ISA level 2: the r6000.  */
00210       arch = bfd_arch_mips;
00211       mach = bfd_mach_mips6000;
00212       break;
00213 
00214     case MIPS_MAGIC_LITTLE3:
00215     case MIPS_MAGIC_BIG3:
00216       /* MIPS ISA level 3: the r4000.  */
00217       arch = bfd_arch_mips;
00218       mach = bfd_mach_mips4000;
00219       break;
00220 
00221     case ALPHA_MAGIC:
00222       arch = bfd_arch_alpha;
00223       mach = 0;
00224       break;
00225 
00226     default:
00227       arch = bfd_arch_obscure;
00228       mach = 0;
00229       break;
00230     }
00231 
00232   return bfd_default_set_arch_mach (abfd, arch, mach);
00233 }
00234 
00235 /* Get the magic number to use based on the architecture and machine.
00236    This is the inverse of _bfd_ecoff_set_arch_mach_hook, above.  */
00237 
00238 static int
00239 ecoff_get_magic (bfd *abfd)
00240 {
00241   int big, little;
00242 
00243   switch (bfd_get_arch (abfd))
00244     {
00245     case bfd_arch_mips:
00246       switch (bfd_get_mach (abfd))
00247        {
00248        default:
00249        case 0:
00250        case bfd_mach_mips3000:
00251          big = MIPS_MAGIC_BIG;
00252          little = MIPS_MAGIC_LITTLE;
00253          break;
00254 
00255        case bfd_mach_mips6000:
00256          big = MIPS_MAGIC_BIG2;
00257          little = MIPS_MAGIC_LITTLE2;
00258          break;
00259 
00260        case bfd_mach_mips4000:
00261          big = MIPS_MAGIC_BIG3;
00262          little = MIPS_MAGIC_LITTLE3;
00263          break;
00264        }
00265 
00266       return bfd_big_endian (abfd) ? big : little;
00267 
00268     case bfd_arch_alpha:
00269       return ALPHA_MAGIC;
00270 
00271     default:
00272       abort ();
00273       return 0;
00274     }
00275 }
00276 
00277 /* Get the section s_flags to use for a section.  */
00278 
00279 static long
00280 ecoff_sec_to_styp_flags (const char *name, flagword flags)
00281 {
00282   unsigned int i;
00283   static struct
00284   {
00285     const char * name;
00286     long flags;
00287   }
00288   styp_flags [] =
00289   {
00290     { _TEXT,    STYP_TEXT       },
00291     { _DATA,    STYP_DATA       },
00292     { _SDATA,   STYP_SDATA      },
00293     { _RDATA,   STYP_RDATA      },
00294     { _LITA,    STYP_LITA       },
00295     { _LIT8,    STYP_LIT8       },
00296     { _LIT4,    STYP_LIT4       },
00297     { _BSS,     STYP_BSS        },
00298     { _SBSS,    STYP_SBSS       },
00299     { _INIT,    STYP_ECOFF_INIT },
00300     { _FINI,    STYP_ECOFF_FINI },
00301     { _PDATA,   STYP_PDATA      },
00302     { _XDATA,   STYP_XDATA      },
00303     { _LIB,     STYP_ECOFF_LIB  },
00304     { _GOT,     STYP_GOT        },
00305     { _HASH,    STYP_HASH       },
00306     { _DYNAMIC, STYP_DYNAMIC    },
00307     { _LIBLIST, STYP_LIBLIST    },
00308     { _RELDYN,  STYP_RELDYN     },
00309     { _CONFLIC, STYP_CONFLIC    },
00310     { _DYNSTR,  STYP_DYNSTR     },
00311     { _DYNSYM,  STYP_DYNSYM     },
00312     { _RCONST,  STYP_RCONST     }
00313   };
00314   long styp = 0;
00315 
00316   for (i = 0; i < ARRAY_SIZE (styp_flags); i++)
00317     if (streq (name, styp_flags[i].name))
00318       {
00319        styp = styp_flags[i].flags;
00320        break;
00321       }
00322 
00323   if (styp == 0)
00324     {
00325       if (streq (name, _COMMENT))
00326        {
00327          styp = STYP_COMMENT;
00328          flags &=~ SEC_NEVER_LOAD;
00329        }
00330       else if (flags & SEC_CODE)
00331        styp = STYP_TEXT;
00332       else if (flags & SEC_DATA)
00333        styp = STYP_DATA;
00334       else if (flags & SEC_READONLY)
00335        styp = STYP_RDATA;
00336       else if (flags & SEC_LOAD)
00337        styp = STYP_REG;
00338       else
00339        styp = STYP_BSS;
00340     }
00341 
00342   if (flags & SEC_NEVER_LOAD)
00343     styp |= STYP_NOLOAD;
00344 
00345   return styp;
00346 }
00347 
00348 /* Get the BFD flags to use for a section.  */
00349 
00350 bfd_boolean
00351 _bfd_ecoff_styp_to_sec_flags (bfd *abfd ATTRIBUTE_UNUSED,
00352                            void * hdr,
00353                            const char *name ATTRIBUTE_UNUSED,
00354                            asection *section ATTRIBUTE_UNUSED,
00355                            flagword * flags_ptr)
00356 {
00357   struct internal_scnhdr *internal_s = hdr;
00358   long styp_flags = internal_s->s_flags;
00359   flagword sec_flags = 0;
00360 
00361   if (styp_flags & STYP_NOLOAD)
00362     sec_flags |= SEC_NEVER_LOAD;
00363 
00364   /* For 386 COFF, at least, an unloadable text or data section is
00365      actually a shared library section.  */
00366   if ((styp_flags & STYP_TEXT)
00367       || (styp_flags & STYP_ECOFF_INIT)
00368       || (styp_flags & STYP_ECOFF_FINI)
00369       || (styp_flags & STYP_DYNAMIC)
00370       || (styp_flags & STYP_LIBLIST)
00371       || (styp_flags & STYP_RELDYN)
00372       || styp_flags == STYP_CONFLIC
00373       || (styp_flags & STYP_DYNSTR)
00374       || (styp_flags & STYP_DYNSYM)
00375       || (styp_flags & STYP_HASH))
00376     {
00377       if (sec_flags & SEC_NEVER_LOAD)
00378        sec_flags |= SEC_CODE | SEC_COFF_SHARED_LIBRARY;
00379       else
00380        sec_flags |= SEC_CODE | SEC_LOAD | SEC_ALLOC;
00381     }
00382   else if ((styp_flags & STYP_DATA)
00383           || (styp_flags & STYP_RDATA)
00384           || (styp_flags & STYP_SDATA)
00385           || styp_flags == STYP_PDATA
00386           || styp_flags == STYP_XDATA
00387           || (styp_flags & STYP_GOT)
00388           || styp_flags == STYP_RCONST)
00389     {
00390       if (sec_flags & SEC_NEVER_LOAD)
00391        sec_flags |= SEC_DATA | SEC_COFF_SHARED_LIBRARY;
00392       else
00393        sec_flags |= SEC_DATA | SEC_LOAD | SEC_ALLOC;
00394       if ((styp_flags & STYP_RDATA)
00395          || styp_flags == STYP_PDATA
00396          || styp_flags == STYP_RCONST)
00397        sec_flags |= SEC_READONLY;
00398     }
00399   else if ((styp_flags & STYP_BSS)
00400           || (styp_flags & STYP_SBSS))
00401     sec_flags |= SEC_ALLOC;
00402   else if ((styp_flags & STYP_INFO) || styp_flags == STYP_COMMENT)
00403     sec_flags |= SEC_NEVER_LOAD;
00404   else if ((styp_flags & STYP_LITA)
00405           || (styp_flags & STYP_LIT8)
00406           || (styp_flags & STYP_LIT4))
00407     sec_flags |= SEC_DATA | SEC_LOAD | SEC_ALLOC | SEC_READONLY;
00408   else if (styp_flags & STYP_ECOFF_LIB)
00409     sec_flags |= SEC_COFF_SHARED_LIBRARY;
00410   else
00411     sec_flags |= SEC_ALLOC | SEC_LOAD;
00412 
00413   * flags_ptr = sec_flags;
00414   return TRUE;
00415 }
00416 
00417 /* Read in the symbolic header for an ECOFF object file.  */
00418 
00419 static bfd_boolean
00420 ecoff_slurp_symbolic_header (bfd *abfd)
00421 {
00422   const struct ecoff_backend_data * const backend = ecoff_backend (abfd);
00423   bfd_size_type external_hdr_size;
00424   void * raw = NULL;
00425   HDRR *internal_symhdr;
00426 
00427   /* See if we've already read it in.  */
00428   if (ecoff_data (abfd)->debug_info.symbolic_header.magic ==
00429       backend->debug_swap.sym_magic)
00430     return TRUE;
00431 
00432   /* See whether there is a symbolic header.  */
00433   if (ecoff_data (abfd)->sym_filepos == 0)
00434     {
00435       bfd_get_symcount (abfd) = 0;
00436       return TRUE;
00437     }
00438 
00439   /* At this point bfd_get_symcount (abfd) holds the number of symbols
00440      as read from the file header, but on ECOFF this is always the
00441      size of the symbolic information header.  It would be cleaner to
00442      handle this when we first read the file in coffgen.c.  */
00443   external_hdr_size = backend->debug_swap.external_hdr_size;
00444   if (bfd_get_symcount (abfd) != external_hdr_size)
00445     {
00446       bfd_set_error (bfd_error_bad_value);
00447       return FALSE;
00448     }
00449 
00450   /* Read the symbolic information header.  */
00451   raw = bfd_malloc (external_hdr_size);
00452   if (raw == NULL)
00453     goto error_return;
00454 
00455   if (bfd_seek (abfd, ecoff_data (abfd)->sym_filepos, SEEK_SET) != 0
00456       || bfd_bread (raw, external_hdr_size, abfd) != external_hdr_size)
00457     goto error_return;
00458   internal_symhdr = &ecoff_data (abfd)->debug_info.symbolic_header;
00459   (*backend->debug_swap.swap_hdr_in) (abfd, raw, internal_symhdr);
00460 
00461   if (internal_symhdr->magic != backend->debug_swap.sym_magic)
00462     {
00463       bfd_set_error (bfd_error_bad_value);
00464       goto error_return;
00465     }
00466 
00467   /* Now we can get the correct number of symbols.  */
00468   bfd_get_symcount (abfd) = (internal_symhdr->isymMax
00469                           + internal_symhdr->iextMax);
00470 
00471   if (raw != NULL)
00472     free (raw);
00473   return TRUE;
00474  error_return:
00475   if (raw != NULL)
00476     free (raw);
00477   return FALSE;
00478 }
00479 
00480 /* Read in and swap the important symbolic information for an ECOFF
00481    object file.  This is called by gdb via the read_debug_info entry
00482    point in the backend structure.  */
00483 
00484 bfd_boolean
00485 _bfd_ecoff_slurp_symbolic_info (bfd *abfd,
00486                             asection *ignore ATTRIBUTE_UNUSED,
00487                             struct ecoff_debug_info *debug)
00488 {
00489   const struct ecoff_backend_data * const backend = ecoff_backend (abfd);
00490   HDRR *internal_symhdr;
00491   bfd_size_type raw_base;
00492   bfd_size_type raw_size;
00493   void * raw;
00494   bfd_size_type external_fdr_size;
00495   char *fraw_src;
00496   char *fraw_end;
00497   struct fdr *fdr_ptr;
00498   bfd_size_type raw_end;
00499   bfd_size_type cb_end;
00500   bfd_size_type amt;
00501   file_ptr pos;
00502 
00503   BFD_ASSERT (debug == &ecoff_data (abfd)->debug_info);
00504 
00505   /* Check whether we've already gotten it, and whether there's any to
00506      get.  */
00507   if (ecoff_data (abfd)->raw_syments != NULL)
00508     return TRUE;
00509   if (ecoff_data (abfd)->sym_filepos == 0)
00510     {
00511       bfd_get_symcount (abfd) = 0;
00512       return TRUE;
00513     }
00514 
00515   if (! ecoff_slurp_symbolic_header (abfd))
00516     return FALSE;
00517 
00518   internal_symhdr = &debug->symbolic_header;
00519 
00520   /* Read all the symbolic information at once.  */
00521   raw_base = (ecoff_data (abfd)->sym_filepos
00522              + backend->debug_swap.external_hdr_size);
00523 
00524   /* Alpha ecoff makes the determination of raw_size difficult. It has
00525      an undocumented debug data section between the symhdr and the first
00526      documented section. And the ordering of the sections varies between
00527      statically and dynamically linked executables.
00528      If bfd supports SEEK_END someday, this code could be simplified.  */
00529   raw_end = 0;
00530 
00531 #define UPDATE_RAW_END(start, count, size) \
00532   cb_end = internal_symhdr->start + internal_symhdr->count * (size); \
00533   if (cb_end > raw_end) \
00534     raw_end = cb_end
00535 
00536   UPDATE_RAW_END (cbLineOffset, cbLine, sizeof (unsigned char));
00537   UPDATE_RAW_END (cbDnOffset, idnMax, backend->debug_swap.external_dnr_size);
00538   UPDATE_RAW_END (cbPdOffset, ipdMax, backend->debug_swap.external_pdr_size);
00539   UPDATE_RAW_END (cbSymOffset, isymMax, backend->debug_swap.external_sym_size);
00540   /* eraxxon@alumni.rice.edu: ioptMax refers to the size of the
00541      optimization symtab, not the number of entries.  */
00542   UPDATE_RAW_END (cbOptOffset, ioptMax, sizeof (char));
00543   UPDATE_RAW_END (cbAuxOffset, iauxMax, sizeof (union aux_ext));
00544   UPDATE_RAW_END (cbSsOffset, issMax, sizeof (char));
00545   UPDATE_RAW_END (cbSsExtOffset, issExtMax, sizeof (char));
00546   UPDATE_RAW_END (cbFdOffset, ifdMax, backend->debug_swap.external_fdr_size);
00547   UPDATE_RAW_END (cbRfdOffset, crfd, backend->debug_swap.external_rfd_size);
00548   UPDATE_RAW_END (cbExtOffset, iextMax, backend->debug_swap.external_ext_size);
00549 
00550 #undef UPDATE_RAW_END
00551 
00552   raw_size = raw_end - raw_base;
00553   if (raw_size == 0)
00554     {
00555       ecoff_data (abfd)->sym_filepos = 0;
00556       return TRUE;
00557     }
00558   raw = bfd_alloc (abfd, raw_size);
00559   if (raw == NULL)
00560     return FALSE;
00561 
00562   pos = ecoff_data (abfd)->sym_filepos;
00563   pos += backend->debug_swap.external_hdr_size;
00564   if (bfd_seek (abfd, pos, SEEK_SET) != 0
00565       || bfd_bread (raw, raw_size, abfd) != raw_size)
00566     {
00567       bfd_release (abfd, raw);
00568       return FALSE;
00569     }
00570 
00571   ecoff_data (abfd)->raw_syments = raw;
00572 
00573   /* Get pointers for the numeric offsets in the HDRR structure.  */
00574 #define FIX(off1, off2, type)                           \
00575   if (internal_symhdr->off1 == 0)                \
00576     debug->off2 = NULL;                                 \
00577   else                                           \
00578     debug->off2 = (type) ((char *) raw                  \
00579                        + (internal_symhdr->off1  \
00580                           - raw_base))
00581 
00582   FIX (cbLineOffset, line, unsigned char *);
00583   FIX (cbDnOffset, external_dnr, void *);
00584   FIX (cbPdOffset, external_pdr, void *);
00585   FIX (cbSymOffset, external_sym, void *);
00586   FIX (cbOptOffset, external_opt, void *);
00587   FIX (cbAuxOffset, external_aux, union aux_ext *);
00588   FIX (cbSsOffset, ss, char *);
00589   FIX (cbSsExtOffset, ssext, char *);
00590   FIX (cbFdOffset, external_fdr, void *);
00591   FIX (cbRfdOffset, external_rfd, void *);
00592   FIX (cbExtOffset, external_ext, void *);
00593 #undef FIX
00594 
00595   /* I don't want to always swap all the data, because it will just
00596      waste time and most programs will never look at it.  The only
00597      time the linker needs most of the debugging information swapped
00598      is when linking big-endian and little-endian MIPS object files
00599      together, which is not a common occurrence.
00600 
00601      We need to look at the fdr to deal with a lot of information in
00602      the symbols, so we swap them here.  */
00603   amt = internal_symhdr->ifdMax;
00604   amt *= sizeof (struct fdr);
00605   debug->fdr = bfd_alloc (abfd, amt);
00606   if (debug->fdr == NULL)
00607     return FALSE;
00608   external_fdr_size = backend->debug_swap.external_fdr_size;
00609   fdr_ptr = debug->fdr;
00610   fraw_src = (char *) debug->external_fdr;
00611   fraw_end = fraw_src + internal_symhdr->ifdMax * external_fdr_size;
00612   for (; fraw_src < fraw_end; fraw_src += external_fdr_size, fdr_ptr++)
00613     (*backend->debug_swap.swap_fdr_in) (abfd, (void *) fraw_src, fdr_ptr);
00614 
00615   return TRUE;
00616 }
00617 
00618 /* ECOFF symbol table routines.  The ECOFF symbol table is described
00619    in gcc/mips-tfile.c.  */
00620 
00621 /* ECOFF uses two common sections.  One is the usual one, and the
00622    other is for small objects.  All the small objects are kept
00623    together, and then referenced via the gp pointer, which yields
00624    faster assembler code.  This is what we use for the small common
00625    section.  */
00626 static asection ecoff_scom_section;
00627 static asymbol ecoff_scom_symbol;
00628 static asymbol *ecoff_scom_symbol_ptr;
00629 
00630 /* Create an empty symbol.  */
00631 
00632 asymbol *
00633 _bfd_ecoff_make_empty_symbol (bfd *abfd)
00634 {
00635   ecoff_symbol_type *new;
00636   bfd_size_type amt = sizeof (ecoff_symbol_type);
00637 
00638   new = bfd_zalloc (abfd, amt);
00639   if (new == NULL)
00640     return NULL;
00641   new->symbol.section = NULL;
00642   new->fdr = NULL;
00643   new->local = FALSE;
00644   new->native = NULL;
00645   new->symbol.the_bfd = abfd;
00646   return &new->symbol;
00647 }
00648 
00649 /* Set the BFD flags and section for an ECOFF symbol.  */
00650 
00651 static bfd_boolean
00652 ecoff_set_symbol_info (bfd *abfd,
00653                      SYMR *ecoff_sym,
00654                      asymbol *asym,
00655                      int ext,
00656                      int weak)
00657 {
00658   asym->the_bfd = abfd;
00659   asym->value = ecoff_sym->value;
00660   asym->section = &bfd_debug_section;
00661   asym->udata.i = 0;
00662 
00663   /* Most symbol types are just for debugging.  */
00664   switch (ecoff_sym->st)
00665     {
00666     case stGlobal:
00667     case stStatic:
00668     case stLabel:
00669     case stProc:
00670     case stStaticProc:
00671       break;
00672     case stNil:
00673       if (ECOFF_IS_STAB (ecoff_sym))
00674        {
00675          asym->flags = BSF_DEBUGGING;
00676          return TRUE;
00677        }
00678       break;
00679     default:
00680       asym->flags = BSF_DEBUGGING;
00681       return TRUE;
00682     }
00683 
00684   if (weak)
00685     asym->flags = BSF_EXPORT | BSF_WEAK;
00686   else if (ext)
00687     asym->flags = BSF_EXPORT | BSF_GLOBAL;
00688   else
00689     {
00690       asym->flags = BSF_LOCAL;
00691       /* Normally, a local stProc symbol will have a corresponding
00692          external symbol.  We mark the local symbol as a debugging
00693          symbol, in order to prevent nm from printing both out.
00694          Similarly, we mark stLabel and stabs symbols as debugging
00695          symbols.  In both cases, we do want to set the value
00696          correctly based on the symbol class.  */
00697       if (ecoff_sym->st == stProc
00698          || ecoff_sym->st == stLabel
00699          || ECOFF_IS_STAB (ecoff_sym))
00700        asym->flags |= BSF_DEBUGGING;
00701     }
00702 
00703   if (ecoff_sym->st == stProc || ecoff_sym->st == stStaticProc)
00704     asym->flags |= BSF_FUNCTION;
00705 
00706   switch (ecoff_sym->sc)
00707     {
00708     case scNil:
00709       /* Used for compiler generated labels.  Leave them in the
00710         debugging section, and mark them as local.  If BSF_DEBUGGING
00711         is set, then nm does not display them for some reason.  If no
00712         flags are set then the linker whines about them.  */
00713       asym->flags = BSF_LOCAL;
00714       break;
00715     case scText:
00716       asym->section = bfd_make_section_old_way (abfd, _TEXT);
00717       asym->value -= asym->section->vma;
00718       break;
00719     case scData:
00720       asym->section = bfd_make_section_old_way (abfd, _DATA);
00721       asym->value -= asym->section->vma;
00722       break;
00723     case scBss:
00724       asym->section = bfd_make_section_old_way (abfd, _BSS);
00725       asym->value -= asym->section->vma;
00726       break;
00727     case scRegister:
00728       asym->flags = BSF_DEBUGGING;
00729       break;
00730     case scAbs:
00731       asym->section = bfd_abs_section_ptr;
00732       break;
00733     case scUndefined:
00734       asym->section = bfd_und_section_ptr;
00735       asym->flags = 0;
00736       asym->value = 0;
00737       break;
00738     case scCdbLocal:
00739     case scBits:
00740     case scCdbSystem:
00741     case scRegImage:
00742     case scInfo:
00743     case scUserStruct:
00744       asym->flags = BSF_DEBUGGING;
00745       break;
00746     case scSData:
00747       asym->section = bfd_make_section_old_way (abfd, ".sdata");
00748       asym->value -= asym->section->vma;
00749       break;
00750     case scSBss:
00751       asym->section = bfd_make_section_old_way (abfd, ".sbss");
00752       asym->value -= asym->section->vma;
00753       break;
00754     case scRData:
00755       asym->section = bfd_make_section_old_way (abfd, ".rdata");
00756       asym->value -= asym->section->vma;
00757       break;
00758     case scVar:
00759       asym->flags = BSF_DEBUGGING;
00760       break;
00761     case scCommon:
00762       if (asym->value > ecoff_data (abfd)->gp_size)
00763        {
00764          asym->section = bfd_com_section_ptr;
00765          asym->flags = 0;
00766          break;
00767        }
00768       /* Fall through.  */
00769     case scSCommon:
00770       if (ecoff_scom_section.name == NULL)
00771        {
00772          /* Initialize the small common section.  */
00773          ecoff_scom_section.name = SCOMMON;
00774          ecoff_scom_section.flags = SEC_IS_COMMON;
00775          ecoff_scom_section.output_section = &ecoff_scom_section;
00776          ecoff_scom_section.symbol = &ecoff_scom_symbol;
00777          ecoff_scom_section.symbol_ptr_ptr = &ecoff_scom_symbol_ptr;
00778          ecoff_scom_symbol.name = SCOMMON;
00779          ecoff_scom_symbol.flags = BSF_SECTION_SYM;
00780          ecoff_scom_symbol.section = &ecoff_scom_section;
00781          ecoff_scom_symbol_ptr = &ecoff_scom_symbol;
00782        }
00783       asym->section = &ecoff_scom_section;
00784       asym->flags = 0;
00785       break;
00786     case scVarRegister:
00787     case scVariant:
00788       asym->flags = BSF_DEBUGGING;
00789       break;
00790     case scSUndefined:
00791       asym->section = bfd_und_section_ptr;
00792       asym->flags = 0;
00793       asym->value = 0;
00794       break;
00795     case scInit:
00796       asym->section = bfd_make_section_old_way (abfd, ".init");
00797       asym->value -= asym->section->vma;
00798       break;
00799     case scBasedVar:
00800     case scXData:
00801     case scPData:
00802       asym->flags = BSF_DEBUGGING;
00803       break;
00804     case scFini:
00805       asym->section = bfd_make_section_old_way (abfd, ".fini");
00806       asym->value -= asym->section->vma;
00807       break;
00808     case scRConst:
00809       asym->section = bfd_make_section_old_way (abfd, ".rconst");
00810       asym->value -= asym->section->vma;
00811       break;
00812     default:
00813       break;
00814     }
00815 
00816   /* Look for special constructors symbols and make relocation entries
00817      in a special construction section.  These are produced by the
00818      -fgnu-linker argument to g++.  */
00819   if (ECOFF_IS_STAB (ecoff_sym))
00820     {
00821       switch (ECOFF_UNMARK_STAB (ecoff_sym->index))
00822        {
00823        default:
00824          break;
00825 
00826        case N_SETA:
00827        case N_SETT:
00828        case N_SETD:
00829        case N_SETB:
00830          /* Mark the symbol as a constructor.  */
00831          asym->flags |= BSF_CONSTRUCTOR;
00832          break;
00833        }
00834     }
00835   return TRUE;
00836 }
00837 
00838 /* Read an ECOFF symbol table.  */
00839 
00840 bfd_boolean
00841 _bfd_ecoff_slurp_symbol_table (bfd *abfd)
00842 {
00843   const struct ecoff_backend_data * const backend = ecoff_backend (abfd);
00844   const bfd_size_type external_ext_size
00845     = backend->debug_swap.external_ext_size;
00846   const bfd_size_type external_sym_size
00847     = backend->debug_swap.external_sym_size;
00848   void (* const swap_ext_in) (bfd *, void *, EXTR *)
00849     = backend->debug_swap.swap_ext_in;
00850   void (* const swap_sym_in) (bfd *, void *, SYMR *)
00851     = backend->debug_swap.swap_sym_in;
00852   bfd_size_type internal_size;
00853   ecoff_symbol_type *internal;
00854   ecoff_symbol_type *internal_ptr;
00855   char *eraw_src;
00856   char *eraw_end;
00857   FDR *fdr_ptr;
00858   FDR *fdr_end;
00859 
00860   /* If we've already read in the symbol table, do nothing.  */
00861   if (ecoff_data (abfd)->canonical_symbols != NULL)
00862     return TRUE;
00863 
00864   /* Get the symbolic information.  */
00865   if (! _bfd_ecoff_slurp_symbolic_info (abfd, NULL,
00866                                    &ecoff_data (abfd)->debug_info))
00867     return FALSE;
00868   if (bfd_get_symcount (abfd) == 0)
00869     return TRUE;
00870 
00871   internal_size = bfd_get_symcount (abfd);
00872   internal_size *= sizeof (ecoff_symbol_type);
00873   internal = bfd_alloc (abfd, internal_size);
00874   if (internal == NULL)
00875     return FALSE;
00876 
00877   internal_ptr = internal;
00878   eraw_src = (char *) ecoff_data (abfd)->debug_info.external_ext;
00879   eraw_end = (eraw_src
00880              + (ecoff_data (abfd)->debug_info.symbolic_header.iextMax
00881                * external_ext_size));
00882   for (; eraw_src < eraw_end; eraw_src += external_ext_size, internal_ptr++)
00883     {
00884       EXTR internal_esym;
00885 
00886       (*swap_ext_in) (abfd, (void *) eraw_src, &internal_esym);
00887       internal_ptr->symbol.name = (ecoff_data (abfd)->debug_info.ssext
00888                                + internal_esym.asym.iss);
00889       if (!ecoff_set_symbol_info (abfd, &internal_esym.asym,
00890                               &internal_ptr->symbol, 1,
00891                               internal_esym.weakext))
00892        return FALSE;
00893       /* The alpha uses a negative ifd field for section symbols.  */
00894       if (internal_esym.ifd >= 0)
00895        internal_ptr->fdr = (ecoff_data (abfd)->debug_info.fdr
00896                           + internal_esym.ifd);
00897       else
00898        internal_ptr->fdr = NULL;
00899       internal_ptr->local = FALSE;
00900       internal_ptr->native = (void *) eraw_src;
00901     }
00902 
00903   /* The local symbols must be accessed via the fdr's, because the
00904      string and aux indices are relative to the fdr information.  */
00905   fdr_ptr = ecoff_data (abfd)->debug_info.fdr;
00906   fdr_end = fdr_ptr + ecoff_data (abfd)->debug_info.symbolic_header.ifdMax;
00907   for (; fdr_ptr < fdr_end; fdr_ptr++)
00908     {
00909       char *lraw_src;
00910       char *lraw_end;
00911 
00912       lraw_src = ((char *) ecoff_data (abfd)->debug_info.external_sym
00913                 + fdr_ptr->isymBase * external_sym_size);
00914       lraw_end = lraw_src + fdr_ptr->csym * external_sym_size;
00915       for (;
00916           lraw_src < lraw_end;
00917           lraw_src += external_sym_size, internal_ptr++)
00918        {
00919          SYMR internal_sym;
00920 
00921          (*swap_sym_in) (abfd, (void *) lraw_src, &internal_sym);
00922          internal_ptr->symbol.name = (ecoff_data (abfd)->debug_info.ss
00923                                    + fdr_ptr->issBase
00924                                    + internal_sym.iss);
00925          if (!ecoff_set_symbol_info (abfd, &internal_sym,
00926                                   &internal_ptr->symbol, 0, 0))
00927            return FALSE;
00928          internal_ptr->fdr = fdr_ptr;
00929          internal_ptr->local = TRUE;
00930          internal_ptr->native = (void *) lraw_src;
00931        }
00932     }
00933 
00934   ecoff_data (abfd)->canonical_symbols = internal;
00935 
00936   return TRUE;
00937 }
00938 
00939 /* Return the amount of space needed for the canonical symbols.  */
00940 
00941 long
00942 _bfd_ecoff_get_symtab_upper_bound (bfd *abfd)
00943 {
00944   if (! _bfd_ecoff_slurp_symbolic_info (abfd, NULL,
00945                                    &ecoff_data (abfd)->debug_info))
00946     return -1;
00947 
00948   if (bfd_get_symcount (abfd) == 0)
00949     return 0;
00950 
00951   return (bfd_get_symcount (abfd) + 1) * (sizeof (ecoff_symbol_type *));
00952 }
00953 
00954 /* Get the canonical symbols.  */
00955 
00956 long
00957 _bfd_ecoff_canonicalize_symtab (bfd *abfd, asymbol **alocation)
00958 {
00959   unsigned int counter = 0;
00960   ecoff_symbol_type *symbase;
00961   ecoff_symbol_type **location = (ecoff_symbol_type **) alocation;
00962 
00963   if (! _bfd_ecoff_slurp_symbol_table (abfd))
00964     return -1;
00965   if (bfd_get_symcount (abfd) == 0)
00966     return 0;
00967 
00968   symbase = ecoff_data (abfd)->canonical_symbols;
00969   while (counter < bfd_get_symcount (abfd))
00970     {
00971       *(location++) = symbase++;
00972       counter++;
00973     }
00974   *location++ = NULL;
00975   return bfd_get_symcount (abfd);
00976 }
00977 
00978 /* Turn ECOFF type information into a printable string.
00979    ecoff_emit_aggregate and ecoff_type_to_string are from
00980    gcc/mips-tdump.c, with swapping added and used_ptr removed.  */
00981 
00982 /* Write aggregate information to a string.  */
00983 
00984 static void
00985 ecoff_emit_aggregate (bfd *abfd,
00986                     FDR *fdr,
00987                     char *string,
00988                     RNDXR *rndx,
00989                     long isym,
00990                     const char *which)
00991 {
00992   const struct ecoff_debug_swap * const debug_swap =
00993     &ecoff_backend (abfd)->debug_swap;
00994   struct ecoff_debug_info * const debug_info = &ecoff_data (abfd)->debug_info;
00995   unsigned int ifd = rndx->rfd;
00996   unsigned int indx = rndx->index;
00997   const char *name;
00998 
00999   if (ifd == 0xfff)
01000     ifd = isym;
01001 
01002   /* An ifd of -1 is an opaque type.  An escaped index of 0 is a
01003      struct return type of a procedure compiled without -g.  */
01004   if (ifd == 0xffffffff
01005       || (rndx->rfd == 0xfff && indx == 0))
01006     name = "<undefined>";
01007   else if (indx == indexNil)
01008     name = "<no name>";
01009   else
01010     {
01011       SYMR sym;
01012 
01013       if (debug_info->external_rfd == NULL)
01014        fdr = debug_info->fdr + ifd;
01015       else
01016        {
01017          RFDT rfd;
01018 
01019          (*debug_swap->swap_rfd_in) (abfd,
01020                                   ((char *) debug_info->external_rfd
01021                                    + ((fdr->rfdBase + ifd)
01022                                      * debug_swap->external_rfd_size)),
01023                                   &rfd);
01024          fdr = debug_info->fdr + rfd;
01025        }
01026 
01027       indx += fdr->isymBase;
01028 
01029       (*debug_swap->swap_sym_in) (abfd,
01030                               ((char *) debug_info->external_sym
01031                                + indx * debug_swap->external_sym_size),
01032                               &sym);
01033 
01034       name = debug_info->ss + fdr->issBase + sym.iss;
01035     }
01036 
01037   sprintf (string,
01038           "%s %s { ifd = %u, index = %lu }",
01039           which, name, ifd,
01040           ((long) indx
01041            + debug_info->symbolic_header.iextMax));
01042 }
01043 
01044 /* Convert the type information to string format.  */
01045 
01046 static char *
01047 ecoff_type_to_string (bfd *abfd, FDR *fdr, unsigned int indx)
01048 {
01049   union aux_ext *aux_ptr;
01050   int bigendian;
01051   AUXU u;
01052   struct qual
01053   {
01054     unsigned int  type;
01055     int  low_bound;
01056     int  high_bound;
01057     int  stride;
01058   } qualifiers[7];
01059   unsigned int basic_type;
01060   int i;
01061   char buffer1[1024];
01062   static char buffer2[1024];
01063   char *p1 = buffer1;
01064   char *p2 = buffer2;
01065   RNDXR rndx;
01066 
01067   aux_ptr = ecoff_data (abfd)->debug_info.external_aux + fdr->iauxBase;
01068   bigendian = fdr->fBigendian;
01069 
01070   for (i = 0; i < 7; i++)
01071     {
01072       qualifiers[i].low_bound = 0;
01073       qualifiers[i].high_bound = 0;
01074       qualifiers[i].stride = 0;
01075     }
01076 
01077   if (AUX_GET_ISYM (bigendian, &aux_ptr[indx]) == (bfd_vma) -1)
01078     return "-1 (no type)";
01079   _bfd_ecoff_swap_tir_in (bigendian, &aux_ptr[indx++].a_ti, &u.ti);
01080 
01081   basic_type = u.ti.bt;
01082   qualifiers[0].type = u.ti.tq0;
01083   qualifiers[1].type = u.ti.tq1;
01084   qualifiers[2].type = u.ti.tq2;
01085   qualifiers[3].type = u.ti.tq3;
01086   qualifiers[4].type = u.ti.tq4;
01087   qualifiers[5].type = u.ti.tq5;
01088   qualifiers[6].type = tqNil;
01089 
01090   /* Go get the basic type.  */
01091   switch (basic_type)
01092     {
01093     case btNil:                    /* Undefined.  */
01094       strcpy (p1, "nil");
01095       break;
01096 
01097     case btAdr:                    /* Address - integer same size as pointer.  */
01098       strcpy (p1, "address");
01099       break;
01100 
01101     case btChar:            /* Character.  */
01102       strcpy (p1, "char");
01103       break;
01104 
01105     case btUChar:           /* Unsigned character.  */
01106       strcpy (p1, "unsigned char");
01107       break;
01108 
01109     case btShort:           /* Short.  */
01110       strcpy (p1, "short");
01111       break;
01112 
01113     case btUShort:          /* Unsigned short.  */
01114       strcpy (p1, "unsigned short");
01115       break;
01116 
01117     case btInt:                    /* Int.  */
01118       strcpy (p1, "int");
01119       break;
01120 
01121     case btUInt:            /* Unsigned int.  */
01122       strcpy (p1, "unsigned int");
01123       break;
01124 
01125     case btLong:            /* Long.  */
01126       strcpy (p1, "long");
01127       break;
01128 
01129     case btULong:           /* Unsigned long.  */
01130       strcpy (p1, "unsigned long");
01131       break;
01132 
01133     case btFloat:           /* Float (real).  */
01134       strcpy (p1, "float");
01135       break;
01136 
01137     case btDouble:          /* Double (real).  */
01138       strcpy (p1, "double");
01139       break;
01140 
01141       /* Structures add 1-2 aux words:
01142         1st word is [ST_RFDESCAPE, offset] pointer to struct def;
01143         2nd word is file index if 1st word rfd is ST_RFDESCAPE.  */
01144 
01145     case btStruct:          /* Structure (Record).  */
01146       _bfd_ecoff_swap_rndx_in (bigendian, &aux_ptr[indx].a_rndx, &rndx);
01147       ecoff_emit_aggregate (abfd, fdr, p1, &rndx,
01148                          (long) AUX_GET_ISYM (bigendian, &aux_ptr[indx+1]),
01149                          "struct");
01150       indx++;               /* Skip aux words.  */
01151       break;
01152 
01153       /* Unions add 1-2 aux words:
01154         1st word is [ST_RFDESCAPE, offset] pointer to union def;
01155         2nd word is file index if 1st word rfd is ST_RFDESCAPE.  */
01156 
01157     case btUnion:           /* Union.  */
01158       _bfd_ecoff_swap_rndx_in (bigendian, &aux_ptr[indx].a_rndx, &rndx);
01159       ecoff_emit_aggregate (abfd, fdr, p1, &rndx,
01160                          (long) AUX_GET_ISYM (bigendian, &aux_ptr[indx+1]),
01161                          "union");
01162       indx++;               /* Skip aux words.  */
01163       break;
01164 
01165       /* Enumerations add 1-2 aux words:
01166         1st word is [ST_RFDESCAPE, offset] pointer to enum def;
01167         2nd word is file index if 1st word rfd is ST_RFDESCAPE.  */
01168 
01169     case btEnum:            /* Enumeration.  */
01170       _bfd_ecoff_swap_rndx_in (bigendian, &aux_ptr[indx].a_rndx, &rndx);
01171       ecoff_emit_aggregate (abfd, fdr, p1, &rndx,
01172                          (long) AUX_GET_ISYM (bigendian, &aux_ptr[indx+1]),
01173                          "enum");
01174       indx++;               /* Skip aux words.  */
01175       break;
01176 
01177     case btTypedef:         /* Defined via a typedef, isymRef points.  */
01178       strcpy (p1, "typedef");
01179       break;
01180 
01181     case btRange:           /* Subrange of int.  */
01182       strcpy (p1, "subrange");
01183       break;
01184 
01185     case btSet:                    /* Pascal sets.  */
01186       strcpy (p1, "set");
01187       break;
01188 
01189     case btComplex:         /* Fortran complex.  */
01190       strcpy (p1, "complex");
01191       break;
01192 
01193     case btDComplex:        /* Fortran double complex.  */
01194       strcpy (p1, "double complex");
01195       break;
01196 
01197     case btIndirect:        /* Forward or unnamed typedef.  */
01198       strcpy (p1, "forward/unamed typedef");
01199       break;
01200 
01201     case btFixedDec:        /* Fixed Decimal.  */
01202       strcpy (p1, "fixed decimal");
01203       break;
01204 
01205     case btFloatDec:        /* Float Decimal.  */
01206       strcpy (p1, "float decimal");
01207       break;
01208 
01209     case btString:          /* Varying Length Character String.  */
01210       strcpy (p1, "string");
01211       break;
01212 
01213     case btBit:                    /* Aligned Bit String.  */
01214       strcpy (p1, "bit");
01215       break;
01216 
01217     case btPicture:         /* Picture.  */
01218       strcpy (p1, "picture");
01219       break;
01220 
01221     case btVoid:            /* Void.  */
01222       strcpy (p1, "void");
01223       break;
01224 
01225     default:
01226       sprintf (p1, _("Unknown basic type %d"), (int) basic_type);
01227       break;
01228     }
01229 
01230   p1 += strlen (buffer1);
01231 
01232   /* If this is a bitfield, get the bitsize.  */
01233   if (u.ti.fBitfield)
01234     {
01235       int bitsize;
01236 
01237       bitsize = AUX_GET_WIDTH (bigendian, &aux_ptr[indx++]);
01238       sprintf (p1, " : %d", bitsize);
01239       p1 += strlen (buffer1);
01240     }
01241 
01242   /* Deal with any qualifiers.  */
01243   if (qualifiers[0].type != tqNil)
01244     {
01245       /* Snarf up any array bounds in the correct order.  Arrays
01246          store 5 successive words in the aux. table:
01247               word 0 RNDXR to type of the bounds (ie, int)
01248               word 1 Current file descriptor index
01249               word 2 low bound
01250               word 3 high bound (or -1 if [])
01251               word 4 stride size in bits.  */
01252       for (i = 0; i < 7; i++)
01253        {
01254          if (qualifiers[i].type == tqArray)
01255            {
01256              qualifiers[i].low_bound =
01257               AUX_GET_DNLOW (bigendian, &aux_ptr[indx+2]);
01258              qualifiers[i].high_bound =
01259               AUX_GET_DNHIGH (bigendian, &aux_ptr[indx+3]);
01260              qualifiers[i].stride =
01261               AUX_GET_WIDTH (bigendian, &aux_ptr[indx+4]);
01262              indx += 5;
01263            }
01264        }
01265 
01266       /* Now print out the qualifiers.  */
01267       for (i = 0; i < 6; i++)
01268        {
01269          switch (qualifiers[i].type)
01270            {
01271            case tqNil:
01272            case tqMax:
01273              break;
01274 
01275            case tqPtr:
01276              strcpy (p2, "ptr to ");
01277              p2 += sizeof ("ptr to ")-1;
01278              break;
01279 
01280            case tqVol:
01281              strcpy (p2, "volatile ");
01282              p2 += sizeof ("volatile ")-1;
01283              break;
01284 
01285            case tqFar:
01286              strcpy (p2, "far ");
01287              p2 += sizeof ("far ")-1;
01288              break;
01289 
01290            case tqProc:
01291              strcpy (p2, "func. ret. ");
01292              p2 += sizeof ("func. ret. ");
01293              break;
01294 
01295            case tqArray:
01296              {
01297               int first_array = i;
01298               int j;
01299 
01300               /* Print array bounds reversed (ie, in the order the C
01301                  programmer writes them).  C is such a fun language....  */
01302               while (i < 5 && qualifiers[i+1].type == tqArray)
01303                 i++;
01304 
01305               for (j = i; j >= first_array; j--)
01306                 {
01307                   strcpy (p2, "array [");
01308                   p2 += sizeof ("array [")-1;
01309                   if (qualifiers[j].low_bound != 0)
01310                     sprintf (p2,
01311                             "%ld:%ld {%ld bits}",
01312                             (long) qualifiers[j].low_bound,
01313                             (long) qualifiers[j].high_bound,
01314                             (long) qualifiers[j].stride);
01315 
01316                   else if (qualifiers[j].high_bound != -1)
01317                     sprintf (p2,
01318                             "%ld {%ld bits}",
01319                             (long) (qualifiers[j].high_bound + 1),
01320                             (long) (qualifiers[j].stride));
01321 
01322                   else
01323                     sprintf (p2, " {%ld bits}", (long) (qualifiers[j].stride));
01324 
01325                   p2 += strlen (p2);
01326                   strcpy (p2, "] of ");
01327                   p2 += sizeof ("] of ")-1;
01328                 }
01329              }
01330              break;
01331            }
01332        }
01333     }
01334 
01335   strcpy (p2, buffer1);
01336   return buffer2;
01337 }
01338 
01339 /* Return information about ECOFF symbol SYMBOL in RET.  */
01340 
01341 void
01342 _bfd_ecoff_get_symbol_info (bfd *abfd ATTRIBUTE_UNUSED,
01343                          asymbol *symbol,
01344                          symbol_info *ret)
01345 {
01346   bfd_symbol_info (symbol, ret);
01347 }
01348 
01349 /* Return whether this is a local label.  */
01350 
01351 bfd_boolean
01352 _bfd_ecoff_bfd_is_local_label_name (bfd *abfd ATTRIBUTE_UNUSED,
01353                                 const char *name)
01354 {
01355   return name[0] == '$';
01356 }
01357 
01358 /* Print information about an ECOFF symbol.  */
01359 
01360 void
01361 _bfd_ecoff_print_symbol (bfd *abfd,
01362                       void * filep,
01363                       asymbol *symbol,
01364                       bfd_print_symbol_type how)
01365 {
01366   const struct ecoff_debug_swap * const debug_swap
01367     = &ecoff_backend (abfd)->debug_swap;
01368   FILE *file = (FILE *)filep;
01369 
01370   switch (how)
01371     {
01372     case bfd_print_symbol_name:
01373       fprintf (file, "%s", symbol->name);
01374       break;
01375     case bfd_print_symbol_more:
01376       if (ecoffsymbol (symbol)->local)
01377        {
01378          SYMR ecoff_sym;
01379 
01380          (*debug_swap->swap_sym_in) (abfd, ecoffsymbol (symbol)->native,
01381                                   &ecoff_sym);
01382          fprintf (file, "ecoff local ");
01383          fprintf_vma (file, (bfd_vma) ecoff_sym.value);
01384          fprintf (file, " %x %x", (unsigned) ecoff_sym.st,
01385                  (unsigned) ecoff_sym.sc);
01386        }
01387       else
01388        {
01389          EXTR ecoff_ext;
01390 
01391          (*debug_swap->swap_ext_in) (abfd, ecoffsymbol (symbol)->native,
01392                                   &ecoff_ext);
01393          fprintf (file, "ecoff extern ");
01394          fprintf_vma (file, (bfd_vma) ecoff_ext.asym.value);
01395          fprintf (file, " %x %x", (unsigned) ecoff_ext.asym.st,
01396                  (unsigned) ecoff_ext.asym.sc);
01397        }
01398       break;
01399     case bfd_print_symbol_all:
01400       /* Print out the symbols in a reasonable way.  */
01401       {
01402        char type;
01403        int pos;
01404        EXTR ecoff_ext;
01405        char jmptbl;
01406        char cobol_main;
01407        char weakext;
01408 
01409        if (ecoffsymbol (symbol)->local)
01410          {
01411            (*debug_swap->swap_sym_in) (abfd, ecoffsymbol (symbol)->native,
01412                                    &ecoff_ext.asym);
01413            type = 'l';
01414            pos = ((((char *) ecoffsymbol (symbol)->native
01415                    - (char *) ecoff_data (abfd)->debug_info.external_sym)
01416                   / debug_swap->external_sym_size)
01417                  + ecoff_data (abfd)->debug_info.symbolic_header.iextMax);
01418            jmptbl = ' ';
01419            cobol_main = ' ';
01420            weakext = ' ';
01421          }
01422        else
01423          {
01424            (*debug_swap->swap_ext_in) (abfd, ecoffsymbol (symbol)->native,
01425                                    &ecoff_ext);
01426            type = 'e';
01427            pos = (((char *) ecoffsymbol (symbol)->native
01428                   - (char *) ecoff_data (abfd)->debug_info.external_ext)
01429                  / debug_swap->external_ext_size);
01430            jmptbl = ecoff_ext.jmptbl ? 'j' : ' ';
01431            cobol_main = ecoff_ext.cobol_main ? 'c' : ' ';
01432            weakext = ecoff_ext.weakext ? 'w' : ' ';
01433          }
01434 
01435        fprintf (file, "[%3d] %c ",
01436                pos, type);
01437        fprintf_vma (file, (bfd_vma) ecoff_ext.asym.value);
01438        fprintf (file, " st %x sc %x indx %x %c%c%c %s",
01439                (unsigned) ecoff_ext.asym.st,
01440                (unsigned) ecoff_ext.asym.sc,
01441                (unsigned) ecoff_ext.asym.index,
01442                jmptbl, cobol_main, weakext,
01443                symbol->name);
01444 
01445        if (ecoffsymbol (symbol)->fdr != NULL
01446            && ecoff_ext.asym.index != indexNil)
01447          {
01448            FDR *fdr;
01449            unsigned int indx;
01450            int bigendian;
01451            bfd_size_type sym_base;
01452            union aux_ext *aux_base;
01453 
01454            fdr = ecoffsymbol (symbol)->fdr;
01455            indx = ecoff_ext.asym.index;
01456 
01457            /* sym_base is used to map the fdr relative indices which
01458               appear in the file to the position number which we are
01459               using.  */
01460            sym_base = fdr->isymBase;
01461            if (ecoffsymbol (symbol)->local)
01462              sym_base +=
01463               ecoff_data (abfd)->debug_info.symbolic_header.iextMax;
01464 
01465            /* aux_base is the start of the aux entries for this file;
01466               asym.index is an offset from this.  */
01467            aux_base = (ecoff_data (abfd)->debug_info.external_aux
01468                      + fdr->iauxBase);
01469 
01470            /* The aux entries are stored in host byte order; the
01471               order is indicated by a bit in the fdr.  */
01472            bigendian = fdr->fBigendian;
01473 
01474            /* This switch is basically from gcc/mips-tdump.c.  */
01475            switch (ecoff_ext.asym.st)
01476              {
01477              case stNil:
01478              case stLabel:
01479               break;
01480 
01481              case stFile:
01482              case stBlock:
01483               fprintf (file, _("\n      End+1 symbol: %ld"),
01484                       (long) (indx + sym_base));
01485               break;
01486 
01487              case stEnd:
01488               if (ecoff_ext.asym.sc == scText
01489                   || ecoff_ext.asym.sc == scInfo)
01490                 fprintf (file, _("\n      First symbol: %ld"),
01491                         (long) (indx + sym_base));
01492               else
01493                 fprintf (file, _("\n      First symbol: %ld"),
01494                         ((long)
01495                          (AUX_GET_ISYM (bigendian,
01496                                       &aux_base[ecoff_ext.asym.index])
01497                           + sym_base)));
01498               break;
01499 
01500              case stProc:
01501              case stStaticProc:
01502               if (ECOFF_IS_STAB (&ecoff_ext.asym))
01503                 ;
01504               else if (ecoffsymbol (symbol)->local)
01505                 fprintf (file, _("\n      End+1 symbol: %-7ld   Type:  %s"),
01506                         ((long)
01507                          (AUX_GET_ISYM (bigendian,
01508                                       &aux_base[ecoff_ext.asym.index])
01509                           + sym_base)),
01510                         ecoff_type_to_string (abfd, fdr, indx + 1));
01511               else
01512                 fprintf (file, _("\n      Local symbol: %ld"),
01513                         ((long) indx
01514                          + (long) sym_base
01515                          + (ecoff_data (abfd)
01516                             ->debug_info.symbolic_header.iextMax)));
01517               break;
01518 
01519              case stStruct:
01520               fprintf (file, _("\n      struct; End+1 symbol: %ld"),
01521                       (long) (indx + sym_base));
01522               break;
01523 
01524              case stUnion:
01525               fprintf (file, _("\n      union; End+1 symbol: %ld"),
01526                       (long) (indx + sym_base));
01527               break;
01528 
01529              case stEnum:
01530               fprintf (file, _("\n      enum; End+1 symbol: %ld"),
01531                       (long) (indx + sym_base));
01532               break;
01533 
01534              default:
01535               if (! ECOFF_IS_STAB (&ecoff_ext.asym))
01536                 fprintf (file, _("\n      Type: %s"),
01537                         ecoff_type_to_string (abfd, fdr, indx));
01538               break;
01539              }
01540          }
01541       }
01542       break;
01543     }
01544 }
01545 
01546 /* Read in the relocs for a section.  */
01547 
01548 static bfd_boolean
01549 ecoff_slurp_reloc_table (bfd *abfd,
01550                       asection *section,
01551                       asymbol **symbols)
01552 {
01553   const struct ecoff_backend_data * const backend = ecoff_backend (abfd);
01554   arelent *internal_relocs;
01555   bfd_size_type external_reloc_size;
01556   bfd_size_type amt;
01557   char *external_relocs;
01558   arelent *rptr;
01559   unsigned int i;
01560 
01561   if (section->relocation != NULL
01562       || section->reloc_count == 0
01563       || (section->flags & SEC_CONSTRUCTOR) != 0)
01564     return TRUE;
01565 
01566   if (! _bfd_ecoff_slurp_symbol_table (abfd))
01567     return FALSE;
01568 
01569   amt = section->reloc_count;
01570   amt *= sizeof (arelent);
01571   internal_relocs = bfd_alloc (abfd, amt);
01572 
01573   external_reloc_size = backend->external_reloc_size;
01574   amt = external_reloc_size * section->reloc_count;
01575   external_relocs = bfd_alloc (abfd, amt);
01576   if (internal_relocs == NULL || external_relocs == NULL)
01577     return FALSE;
01578   if (bfd_seek (abfd, section->rel_filepos, SEEK_SET) != 0)
01579     return FALSE;
01580   if (bfd_bread (external_relocs, amt, abfd) != amt)
01581     return FALSE;
01582 
01583   for (i = 0, rptr = internal_relocs; i < section->reloc_count; i++, rptr++)
01584     {
01585       struct internal_reloc intern;
01586 
01587       (*backend->swap_reloc_in) (abfd,
01588                              external_relocs + i * external_reloc_size,
01589                              &intern);
01590 
01591       if (intern.r_extern)
01592        {
01593          /* r_symndx is an index into the external symbols.  */
01594          BFD_ASSERT (intern.r_symndx >= 0
01595                     && (intern.r_symndx
01596                        < (ecoff_data (abfd)
01597                           ->debug_info.symbolic_header.iextMax)));
01598          rptr->sym_ptr_ptr = symbols + intern.r_symndx;
01599          rptr->addend = 0;
01600        }
01601       else if (intern.r_symndx == RELOC_SECTION_NONE
01602               || intern.r_symndx == RELOC_SECTION_ABS)
01603        {
01604          rptr->sym_ptr_ptr = bfd_abs_section_ptr->symbol_ptr_ptr;
01605          rptr->addend = 0;
01606        }
01607       else
01608        {
01609          const char *sec_name;
01610          asection *sec;
01611 
01612          /* r_symndx is a section key.  */
01613          switch (intern.r_symndx)
01614            {
01615            case RELOC_SECTION_TEXT:  sec_name = _TEXT;  break;
01616            case RELOC_SECTION_RDATA: sec_name = _RDATA; break;
01617            case RELOC_SECTION_DATA:  sec_name = _DATA;  break;
01618            case RELOC_SECTION_SDATA: sec_name = _SDATA; break;
01619            case RELOC_SECTION_SBSS:  sec_name = _SBSS;  break;
01620            case RELOC_SECTION_BSS:   sec_name = _BSS;   break;
01621            case RELOC_SECTION_INIT:  sec_name = _INIT;  break;
01622            case RELOC_SECTION_LIT8:  sec_name = _LIT8;  break;
01623            case RELOC_SECTION_LIT4:  sec_name = _LIT4;  break;
01624            case RELOC_SECTION_XDATA: sec_name = _XDATA; break;
01625            case RELOC_SECTION_PDATA: sec_name = _PDATA; break;
01626            case RELOC_SECTION_FINI:  sec_name = _FINI;  break;
01627            case RELOC_SECTION_LITA:  sec_name = _LITA;  break;
01628            case RELOC_SECTION_RCONST: sec_name = _RCONST; break;
01629            default: abort ();
01630            }
01631 
01632          sec = bfd_get_section_by_name (abfd, sec_name);
01633          if (sec == NULL)
01634            abort ();
01635          rptr->sym_ptr_ptr = sec->symbol_ptr_ptr;
01636 
01637          rptr->addend = - bfd_get_section_vma (abfd, sec);
01638        }
01639 
01640       rptr->address = intern.r_vaddr - bfd_get_section_vma (abfd, section);
01641 
01642       /* Let the backend select the howto field and do any other
01643         required processing.  */
01644       (*backend->adjust_reloc_in) (abfd, &intern, rptr);
01645     }
01646 
01647   bfd_release (abfd, external_relocs);
01648 
01649   section->relocation = internal_relocs;
01650 
01651   return TRUE;
01652 }
01653 
01654 /* Get a canonical list of relocs.  */
01655 
01656 long
01657 _bfd_ecoff_canonicalize_reloc (bfd *abfd,
01658                             asection *section,
01659                             arelent **relptr,
01660                             asymbol **symbols)
01661 {
01662   unsigned int count;
01663 
01664   if (section->flags & SEC_CONSTRUCTOR)
01665     {
01666       arelent_chain *chain;
01667 
01668       /* This section has relocs made up by us, not the file, so take
01669         them out of their chain and place them into the data area
01670         provided.  */
01671       for (count = 0, chain = section->constructor_chain;
01672           count < section->reloc_count;
01673           count++, chain = chain->next)
01674        *relptr++ = &chain->relent;
01675     }
01676   else
01677     {
01678       arelent *tblptr;
01679 
01680       if (! ecoff_slurp_reloc_table (abfd, section, symbols))
01681        return -1;
01682 
01683       tblptr = section->relocation;
01684 
01685       for (count = 0; count < section->reloc_count; count++)
01686        *relptr++ = tblptr++;
01687     }
01688 
01689   *relptr = NULL;
01690 
01691   return section->reloc_count;
01692 }
01693 
01694 /* Provided a BFD, a section and an offset into the section, calculate
01695    and return the name of the source file and the line nearest to the
01696    wanted location.  */
01697 
01698 bfd_boolean
01699 _bfd_ecoff_find_nearest_line (bfd *abfd,
01700                            asection *section,
01701                            asymbol **ignore_symbols ATTRIBUTE_UNUSED,
01702                            bfd_vma offset,
01703                            const char **filename_ptr,
01704                            const char **functionname_ptr,
01705                            unsigned int *retline_ptr)
01706 {
01707   const struct ecoff_debug_swap * const debug_swap
01708     = &ecoff_backend (abfd)->debug_swap;
01709   struct ecoff_debug_info * const debug_info = &ecoff_data (abfd)->debug_info;
01710   struct ecoff_find_line *line_info;
01711 
01712   /* Make sure we have the FDR's.  */
01713   if (! _bfd_ecoff_slurp_symbolic_info (abfd, NULL, debug_info)
01714       || bfd_get_symcount (abfd) == 0)
01715     return FALSE;
01716 
01717   if (ecoff_data (abfd)->find_line_info == NULL)
01718     {
01719       bfd_size_type amt = sizeof (struct ecoff_find_line);
01720 
01721       ecoff_data (abfd)->find_line_info = bfd_zalloc (abfd, amt);
01722       if (ecoff_data (abfd)->find_line_info == NULL)
01723        return FALSE;
01724     }
01725   line_info = ecoff_data (abfd)->find_line_info;
01726 
01727   return _bfd_ecoff_locate_line (abfd, section, offset, debug_info,
01728                              debug_swap, line_info, filename_ptr,
01729                              functionname_ptr, retline_ptr);
01730 }
01731 
01732 /* Copy private BFD data.  This is called by objcopy and strip.  We
01733    use it to copy the ECOFF debugging information from one BFD to the
01734    other.  It would be theoretically possible to represent the ECOFF
01735    debugging information in the symbol table.  However, it would be a
01736    lot of work, and there would be little gain (gas, gdb, and ld
01737    already access the ECOFF debugging information via the
01738    ecoff_debug_info structure, and that structure would have to be
01739    retained in order to support ECOFF debugging in MIPS ELF).
01740 
01741    The debugging information for the ECOFF external symbols comes from
01742    the symbol table, so this function only handles the other debugging
01743    information.  */
01744 
01745 bfd_boolean
01746 _bfd_ecoff_bfd_copy_private_bfd_data (bfd *ibfd, bfd *obfd)
01747 {
01748   struct ecoff_debug_info *iinfo = &ecoff_data (ibfd)->debug_info;
01749   struct ecoff_debug_info *oinfo = &ecoff_data (obfd)->debug_info;
01750   int i;
01751   asymbol **sym_ptr_ptr;
01752   size_t c;
01753   bfd_boolean local;
01754 
01755   /* We only want to copy information over if both BFD's use ECOFF
01756      format.  */
01757   if (bfd_get_flavour (ibfd) != bfd_target_ecoff_flavour
01758       || bfd_get_flavour (obfd) != bfd_target_ecoff_flavour)
01759     return TRUE;
01760 
01761   /* Copy the GP value and the register masks.  */
01762   ecoff_data (obfd)->gp = ecoff_data (ibfd)->gp;
01763   ecoff_data (obfd)->gprmask = ecoff_data (ibfd)->gprmask;
01764   ecoff_data (obfd)->fprmask = ecoff_data (ibfd)->fprmask;
01765   for (i = 0; i < 3; i++)
01766     ecoff_data (obfd)->cprmask[i] = ecoff_data (ibfd)->cprmask[i];
01767 
01768   /* Copy the version stamp.  */
01769   oinfo->symbolic_header.vstamp = iinfo->symbolic_header.vstamp;
01770 
01771   /* If there are no symbols, don't copy any debugging information.  */
01772   c = bfd_get_symcount (obfd);
01773   sym_ptr_ptr = bfd_get_outsymbols (obfd);
01774   if (c == 0 || sym_ptr_ptr == NULL)
01775     return TRUE;
01776 
01777   /* See if there are any local symbols.  */
01778   local = FALSE;
01779   for (; c > 0; c--, sym_ptr_ptr++)
01780     {
01781       if (ecoffsymbol (*sym_ptr_ptr)->local)
01782        {
01783          local = TRUE;
01784          break;
01785        }
01786     }
01787 
01788   if (local)
01789     {
01790       /* There are some local symbols.  We just bring over all the
01791         debugging information.  FIXME: This is not quite the right
01792         thing to do.  If the user has asked us to discard all
01793         debugging information, then we are probably going to wind up
01794         keeping it because there will probably be some local symbol
01795         which objcopy did not discard.  We should actually break
01796         apart the debugging information and only keep that which
01797         applies to the symbols we want to keep.  */
01798       oinfo->symbolic_header.ilineMax = iinfo->symbolic_header.ilineMax;
01799       oinfo->symbolic_header.cbLine = iinfo->symbolic_header.cbLine;
01800       oinfo->line = iinfo->line;
01801 
01802       oinfo->symbolic_header.idnMax = iinfo->symbolic_header.idnMax;
01803       oinfo->external_dnr = iinfo->external_dnr;
01804 
01805       oinfo->symbolic_header.ipdMax = iinfo->symbolic_header.ipdMax;
01806       oinfo->external_pdr = iinfo->external_pdr;
01807 
01808       oinfo->symbolic_header.isymMax = iinfo->symbolic_header.isymMax;
01809       oinfo->external_sym = iinfo->external_sym;
01810 
01811       oinfo->symbolic_header.ioptMax = iinfo->symbolic_header.ioptMax;
01812       oinfo->external_opt = iinfo->external_opt;
01813 
01814       oinfo->symbolic_header.iauxMax = iinfo->symbolic_header.iauxMax;
01815       oinfo->external_aux = iinfo->external_aux;
01816 
01817       oinfo->symbolic_header.issMax = iinfo->symbolic_header.issMax;
01818       oinfo->ss = iinfo->ss;
01819 
01820       oinfo->symbolic_header.ifdMax = iinfo->symbolic_header.ifdMax;
01821       oinfo->external_fdr = iinfo->external_fdr;
01822 
01823       oinfo->symbolic_header.crfd = iinfo->symbolic_header.crfd;
01824       oinfo->external_rfd = iinfo->external_rfd;
01825     }
01826   else
01827     {
01828       /* We are discarding all the local symbol information.  Look
01829         through the external symbols and remove all references to FDR
01830         or aux information.  */
01831       c = bfd_get_symcount (obfd);
01832       sym_ptr_ptr = bfd_get_outsymbols (obfd);
01833       for (; c > 0; c--, sym_ptr_ptr++)
01834        {
01835          EXTR esym;
01836 
01837          (*(ecoff_backend (obfd)->debug_swap.swap_ext_in))
01838            (obfd, ecoffsymbol (*sym_ptr_ptr)->native, &esym);
01839          esym.ifd = ifdNil;
01840          esym.asym.index = indexNil;
01841          (*(ecoff_backend (obfd)->debug_swap.swap_ext_out))
01842            (obfd, &esym, ecoffsymbol (*sym_ptr_ptr)->native);
01843        }
01844     }
01845 
01846   return TRUE;
01847 }
01848 
01849 /* Set the architecture.  The supported architecture is stored in the
01850    backend pointer.  We always set the architecture anyhow, since many
01851    callers ignore the return value.  */
01852 
01853 bfd_boolean
01854 _bfd_ecoff_set_arch_mach (bfd *abfd,
01855                        enum bfd_architecture arch,
01856                        unsigned long machine)
01857 {
01858   bfd_default_set_arch_mach (abfd, arch, machine);
01859   return arch == ecoff_backend (abfd)->arch;
01860 }
01861 
01862 /* Get the size of the section headers.  */
01863 
01864 int
01865 _bfd_ecoff_sizeof_headers (bfd *abfd,
01866                         struct bfd_link_info *info ATTRIBUTE_UNUSED)
01867 {
01868   asection *current;
01869   int c;
01870   int ret;
01871 
01872   c = 0;
01873   for (current = abfd->sections;
01874        current != NULL;
01875        current = current->next)
01876     ++c;
01877 
01878   ret = (bfd_coff_filhsz (abfd)
01879         + bfd_coff_aoutsz (abfd)
01880         + c * bfd_coff_scnhsz (abfd));
01881   return BFD_ALIGN (ret, 16);
01882 }
01883 
01884 /* Get the contents of a section.  */
01885 
01886 bfd_boolean
01887 _bfd_ecoff_get_section_contents (bfd *abfd,
01888                              asection *section,
01889                              void * location,
01890                              file_ptr offset,
01891                              bfd_size_type count)
01892 {
01893   return _bfd_generic_get_section_contents (abfd, section, location,
01894                                        offset, count);
01895 }
01896 
01897 /* Sort sections by VMA, but put SEC_ALLOC sections first.  This is
01898    called via qsort.  */
01899 
01900 static int
01901 ecoff_sort_hdrs (const void * arg1, const void * arg2)
01902 {
01903   const asection *hdr1 = *(const asection **) arg1;
01904   const asection *hdr2 = *(const asection **) arg2;
01905 
01906   if ((hdr1->flags & SEC_ALLOC) != 0)
01907     {
01908       if ((hdr2->flags & SEC_ALLOC) == 0)
01909        return -1;
01910     }
01911   else
01912     {
01913       if ((hdr2->flags & SEC_ALLOC) != 0)
01914        return 1;
01915     }
01916   if (hdr1->vma < hdr2->vma)
01917     return -1;
01918   else if (hdr1->vma > hdr2->vma)
01919     return 1;
01920   else
01921     return 0;
01922 }
01923 
01924 /* Calculate the file position for each section, and set
01925    reloc_filepos.  */
01926 
01927 static bfd_boolean
01928 ecoff_compute_section_file_positions (bfd *abfd)
01929 {
01930   file_ptr sofar, file_sofar;
01931   asection **sorted_hdrs;
01932   asection *current;
01933   unsigned int i;
01934   file_ptr old_sofar;
01935   bfd_boolean rdata_in_text;
01936   bfd_boolean first_data, first_nonalloc;
01937   const bfd_vma round = ecoff_backend (abfd)->round;
01938   bfd_size_type amt;
01939 
01940   sofar = _bfd_ecoff_sizeof_headers (abfd, NULL);
01941   file_sofar = sofar;
01942 
01943   /* Sort the sections by VMA.  */
01944   amt = abfd->section_count;
01945   amt *= sizeof (asection *);
01946   sorted_hdrs = bfd_malloc (amt);
01947   if (sorted_hdrs == NULL)
01948     return FALSE;
01949   for (current = abfd->sections, i = 0;
01950        current != NULL;
01951        current = current->next, i++)
01952     sorted_hdrs[i] = current;
01953   BFD_ASSERT (i == abfd->section_count);
01954 
01955   qsort (sorted_hdrs, abfd->section_count, sizeof (asection *),
01956         ecoff_sort_hdrs);
01957 
01958   /* Some versions of the OSF linker put the .rdata section in the
01959      text segment, and some do not.  */
01960   rdata_in_text = ecoff_backend (abfd)->rdata_in_text;
01961   if (rdata_in_text)
01962     {
01963       for (i = 0; i < abfd->section_count; i++)
01964        {
01965          current = sorted_hdrs[i];
01966          if (streq (current->name, _RDATA))
01967            break;
01968          if ((current->flags & SEC_CODE) == 0
01969              && ! streq (current->name, _PDATA)
01970              && ! streq (current->name, _RCONST))
01971            {
01972              rdata_in_text = FALSE;
01973              break;
01974            }
01975        }
01976     }
01977   ecoff_data (abfd)->rdata_in_text = rdata_in_text;
01978 
01979   first_data = TRUE;
01980   first_nonalloc = TRUE;
01981   for (i = 0; i < abfd->section_count; i++)
01982     {
01983       unsigned int alignment_power;
01984 
01985       current = sorted_hdrs[i];
01986 
01987       /* For the Alpha ECOFF .pdata section the lnnoptr field is
01988         supposed to indicate the number of .pdata entries that are
01989         really in the section.  Each entry is 8 bytes.  We store this
01990         away in line_filepos before increasing the section size.  */
01991       if (streq (current->name, _PDATA))
01992        current->line_filepos = current->size / 8;
01993 
01994       alignment_power = current->alignment_power;
01995 
01996       /* On Ultrix, the data sections in an executable file must be
01997         aligned to a page boundary within the file.  This does not
01998         affect the section size, though.  FIXME: Does this work for
01999         other platforms?  It requires some modification for the
02000         Alpha, because .rdata on the Alpha goes with the text, not
02001         the data.  */
02002       if ((abfd->flags & EXEC_P) != 0
02003          && (abfd->flags & D_PAGED) != 0
02004          && ! first_data
02005          && (current->flags & SEC_CODE) == 0
02006          && (! rdata_in_text
02007              || ! streq (current->name, _RDATA))
02008          && ! streq (current->name, _PDATA)
02009          && ! streq (current->name, _RCONST))
02010        {
02011          sofar = (sofar + round - 1) &~ (round - 1);
02012          file_sofar = (file_sofar + round - 1) &~ (round - 1);
02013          first_data = FALSE;
02014        }
02015       else if (streq (current->name, _LIB))
02016        {
02017          /* On Irix 4, the location of contents of the .lib section
02018             from a shared library section is also rounded up to a
02019             page boundary.  */
02020 
02021          sofar = (sofar + round - 1) &~ (round - 1);
02022          file_sofar = (file_sofar + round - 1) &~ (round - 1);
02023        }
02024       else if (first_nonalloc
02025               && (current->flags & SEC_ALLOC) == 0
02026               && (abfd->flags & D_PAGED) != 0)
02027        {
02028          /* Skip up to the next page for an unallocated section, such
02029              as the .comment section on the Alpha.  This leaves room
02030              for the .bss section.  */
02031          first_nonalloc = FALSE;
02032          sofar = (sofar + round - 1) &~ (round - 1);
02033          file_sofar = (file_sofar + round - 1) &~ (round - 1);
02034        }
02035 
02036       /* Align the sections in the file to the same boundary on
02037         which they are aligned in virtual memory.  */
02038       sofar = BFD_ALIGN (sofar, 1 << alignment_power);
02039       if ((current->flags & SEC_HAS_CONTENTS) != 0)
02040        file_sofar = BFD_ALIGN (file_sofar, 1 << alignment_power);
02041 
02042       if ((abfd->flags & D_PAGED) != 0
02043          && (current->flags & SEC_ALLOC) != 0)
02044        {
02045          sofar += (current->vma - sofar) % round;
02046          if ((current->flags & SEC_HAS_CONTENTS) != 0)
02047            file_sofar += (current->vma - file_sofar) % round;
02048        }
02049 
02050       if ((current->flags & (SEC_HAS_CONTENTS | SEC_LOAD)) != 0)
02051        current->filepos = file_sofar;
02052 
02053       sofar += current->size;
02054       if ((current->flags & SEC_HAS_CONTENTS) != 0)
02055        file_sofar += current->size;
02056 
02057       /* Make sure that this section is of the right size too.  */
02058       old_sofar = sofar;
02059       sofar = BFD_ALIGN (sofar, 1 << alignment_power);
02060       if ((current->flags & SEC_HAS_CONTENTS) != 0)
02061        file_sofar = BFD_ALIGN (file_sofar, 1 << alignment_power);
02062       current->size += sofar - old_sofar;
02063     }
02064 
02065   free (sorted_hdrs);
02066   sorted_hdrs = NULL;
02067 
02068   ecoff_data (abfd)->reloc_filepos = file_sofar;
02069 
02070   return TRUE;
02071 }
02072 
02073 /* Determine the location of the relocs for all the sections in the
02074    output file, as well as the location of the symbolic debugging
02075    information.  */
02076 
02077 static bfd_size_type
02078 ecoff_compute_reloc_file_positions (bfd *abfd)
02079 {
02080   const bfd_size_type external_reloc_size =
02081     ecoff_backend (abfd)->external_reloc_size;
02082   file_ptr reloc_base;
02083   bfd_size_type reloc_size;
02084   asection *current;
02085   file_ptr sym_base;
02086 
02087   if (! abfd->output_has_begun)
02088     {
02089       if (! ecoff_compute_section_file_positions (abfd))
02090        abort ();
02091       abfd->output_has_begun = TRUE;
02092     }
02093 
02094   reloc_base = ecoff_data (abfd)->reloc_filepos;
02095 
02096   reloc_size = 0;
02097   for (current = abfd->sections;
02098        current != NULL;
02099        current = current->next)
02100     {
02101       if (current->reloc_count == 0)
02102        current->rel_filepos = 0;
02103       else
02104        {
02105          bfd_size_type relsize;
02106 
02107          current->rel_filepos = reloc_base;
02108          relsize = current->reloc_count * external_reloc_size;
02109          reloc_size += relsize;
02110          reloc_base += relsize;
02111        }
02112     }
02113 
02114   sym_base = ecoff_data (abfd)->reloc_filepos + reloc_size;
02115 
02116   /* At least on Ultrix, the symbol table of an executable file must
02117      be aligned to a page boundary.  FIXME: Is this true on other
02118      platforms?  */
02119   if ((abfd->flags & EXEC_P) != 0
02120       && (abfd->flags & D_PAGED) != 0)
02121     sym_base = ((sym_base + ecoff_backend (abfd)->round - 1)
02122               &~ (ecoff_backend (abfd)->round - 1));
02123 
02124   ecoff_data (abfd)->sym_filepos = sym_base;
02125 
02126   return reloc_size;
02127 }
02128 
02129 /* Set the contents of a section.  */
02130 
02131 bfd_boolean
02132 _bfd_ecoff_set_section_contents (bfd *abfd,
02133                              asection *section,
02134                              const void * location,
02135                              file_ptr offset,
02136                              bfd_size_type count)
02137 {
02138   file_ptr pos;
02139 
02140   /* This must be done first, because bfd_set_section_contents is
02141      going to set output_has_begun to TRUE.  */
02142   if (! abfd->output_has_begun
02143       && ! ecoff_compute_section_file_positions (abfd))
02144     return FALSE;
02145 
02146   /* Handle the .lib section specially so that Irix 4 shared libraries
02147      work out.  See coff_set_section_contents in coffcode.h.  */
02148   if (streq (section->name, _LIB))
02149     {
02150       bfd_byte *rec, *recend;
02151 
02152       rec = (bfd_byte *) location;
02153       recend = rec + count;
02154       while (rec < recend)
02155        {
02156          ++section->lma;
02157          rec += bfd_get_32 (abfd, rec) * 4;
02158        }
02159 
02160       BFD_ASSERT (rec == recend);
02161     }
02162 
02163   if (count == 0)
02164     return TRUE;
02165 
02166   pos = section->filepos + offset;
02167   if (bfd_seek (abfd, pos, SEEK_SET) != 0
02168       || bfd_bwrite (location, count, abfd) != count)
02169     return FALSE;
02170 
02171   return TRUE;
02172 }
02173 
02174 /* Get the GP value for an ECOFF file.  This is a hook used by
02175    nlmconv.  */
02176 
02177 bfd_vma
02178 bfd_ecoff_get_gp_value (bfd *abfd)
02179 {
02180   if (bfd_get_flavour (abfd) != bfd_target_ecoff_flavour
02181       || bfd_get_format (abfd) != bfd_object)
02182     {
02183       bfd_set_error (bfd_error_invalid_operation);
02184       return 0;
02185     }
02186 
02187   return ecoff_data (abfd)->gp;
02188 }
02189 
02190 /* Set the GP value for an ECOFF file.  This is a hook used by the
02191    assembler.  */
02192 
02193 bfd_boolean
02194 bfd_ecoff_set_gp_value (bfd *abfd, bfd_vma gp_value)
02195 {
02196   if (bfd_get_flavour (abfd) != bfd_target_ecoff_flavour
02197       || bfd_get_format (abfd) != bfd_object)
02198     {
02199       bfd_set_error (bfd_error_invalid_operation);
02200       return FALSE;
02201     }
02202 
02203   ecoff_data (abfd)->gp = gp_value;
02204 
02205   return TRUE;
02206 }
02207 
02208 /* Set the register masks for an ECOFF file.  This is a hook used by
02209    the assembler.  */
02210 
02211 bfd_boolean
02212 bfd_ecoff_set_regmasks (bfd *abfd,
02213                      unsigned long gprmask,
02214                      unsigned long fprmask,
02215                      unsigned long *cprmask)
02216 {
02217   ecoff_data_type *tdata;
02218 
02219   if (bfd_get_flavour (abfd) != bfd_target_ecoff_flavour
02220       || bfd_get_format (abfd) != bfd_object)
02221     {
02222       bfd_set_error (bfd_error_invalid_operation);
02223       return FALSE;
02224     }
02225 
02226   tdata = ecoff_data (abfd);
02227   tdata->gprmask = gprmask;
02228   tdata->fprmask = fprmask;
02229   if (cprmask != NULL)
02230     {
02231       int i;
02232 
02233       for (i = 0; i < 3; i++)
02234        tdata->cprmask[i] = cprmask[i];
02235     }
02236 
02237   return TRUE;
02238 }
02239 
02240 /* Get ECOFF EXTR information for an external symbol.  This function
02241    is passed to bfd_ecoff_debug_externals.  */
02242 
02243 static bfd_boolean
02244 ecoff_get_extr (asymbol *sym, EXTR *esym)
02245 {
02246   ecoff_symbol_type *ecoff_sym_ptr;
02247   bfd *input_bfd;
02248 
02249   if (bfd_asymbol_flavour (sym) != bfd_target_ecoff_flavour
02250       || ecoffsymbol (sym)->native == NULL)
02251     {
02252       /* Don't include debugging, local, or section symbols.  */
02253       if ((sym->flags & BSF_DEBUGGING) != 0
02254          || (sym->flags & BSF_LOCAL) != 0
02255          || (sym->flags & BSF_SECTION_SYM) != 0)
02256        return FALSE;
02257 
02258       esym->jmptbl = 0;
02259       esym->cobol_main = 0;
02260       esym->weakext = (sym->flags & BSF_WEAK) != 0;
02261       esym->reserved = 0;
02262       esym->ifd = ifdNil;
02263       /* FIXME: we can do better than this for st and sc.  */
02264       esym->asym.st = stGlobal;
02265       esym->asym.sc = scAbs;
02266       esym->asym.reserved = 0;
02267       esym->asym.index = indexNil;
02268       return TRUE;
02269     }
02270 
02271   ecoff_sym_ptr = ecoffsymbol (sym);
02272 
02273   if (ecoff_sym_ptr->local)
02274     return FALSE;
02275 
02276   input_bfd = bfd_asymbol_bfd (sym);
02277   (*(ecoff_backend (input_bfd)->debug_swap.swap_ext_in))
02278     (input_bfd, ecoff_sym_ptr->native, esym);
02279 
02280   /* If the symbol was defined by the linker, then esym will be
02281      undefined but sym will not be.  Get a better class for such a
02282      symbol.  */
02283   if ((esym->asym.sc == scUndefined
02284        || esym->asym.sc == scSUndefined)
02285       && ! bfd_is_und_section (bfd_get_section (sym)))
02286     esym->asym.sc = scAbs;
02287 
02288   /* Adjust the FDR index for the symbol by that used for the input
02289      BFD.  */
02290   if (esym->ifd != -1)
02291     {
02292       struct ecoff_debug_info *input_debug;
02293 
02294       input_debug = &ecoff_data (input_bfd)->debug_info;
02295       BFD_ASSERT (esym->ifd < input_debug->symbolic_header.ifdMax);
02296       if (input_debug->ifdmap != NULL)
02297        esym->ifd = input_debug->ifdmap[esym->ifd];
02298     }
02299 
02300   return TRUE;
02301 }
02302 
02303 /* Set the external symbol index.  This routine is passed to
02304    bfd_ecoff_debug_externals.  */
02305 
02306 static void
02307 ecoff_set_index (asymbol *sym, bfd_size_type indx)
02308 {
02309   ecoff_set_sym_index (sym, indx);
02310 }
02311 
02312 /* Write out an ECOFF file.  */
02313 
02314 bfd_boolean
02315 _bfd_ecoff_write_object_contents (bfd *abfd)
02316 {
02317   const struct ecoff_backend_data * const backend = ecoff_backend (abfd);
02318   const bfd_vma round = backend->round;
02319   const bfd_size_type filhsz = bfd_coff_filhsz (abfd);
02320   const bfd_size_type aoutsz = bfd_coff_aoutsz (abfd);
02321   const bfd_size_type scnhsz = bfd_coff_scnhsz (abfd);
02322   const bfd_size_type external_hdr_size
02323     = backend->debug_swap.external_hdr_size;
02324   const bfd_size_type external_reloc_size = backend->external_reloc_size;
02325   void (* const adjust_reloc_out) (bfd *, const arelent *, struct internal_reloc *)
02326     = backend->adjust_reloc_out;
02327   void (* const swap_reloc_out) (bfd *, const struct internal_reloc *, void *)
02328     = backend->swap_reloc_out;
02329   struct ecoff_debug_info * const debug = &ecoff_data (abfd)->debug_info;
02330   HDRR * const symhdr = &debug->symbolic_header;
02331   asection *current;
02332   unsigned int count;
02333   bfd_size_type reloc_size;
02334   bfd_size_type text_size;
02335   bfd_vma text_start;
02336   bfd_boolean set_text_start;
02337   bfd_size_type data_size;
02338   bfd_vma data_start;
02339   bfd_boolean set_data_start;
02340   bfd_size_type bss_size;
02341   void * buff = NULL;
02342   void * reloc_buff = NULL;
02343   struct internal_filehdr internal_f;
02344   struct internal_aouthdr internal_a;
02345   int i;
02346 
02347   /* Determine where the sections and relocs will go in the output
02348      file.  */
02349   reloc_size = ecoff_compute_reloc_file_positions (abfd);
02350 
02351   count = 1;
02352   for (current = abfd->sections;
02353        current != NULL;
02354        current = current->next)
02355     {
02356       current->target_index = count;
02357       ++count;
02358     }
02359 
02360   if ((abfd->flags & D_PAGED) != 0)
02361     text_size = _bfd_ecoff_sizeof_headers (abfd, NULL);
02362   else
02363     text_size = 0;
02364   text_start = 0;
02365   set_text_start = FALSE;
02366   data_size = 0;
02367   data_start = 0;
02368   set_data_start = FALSE;
02369   bss_size = 0;
02370 
02371   /* Write section headers to the file.  */
02372 
02373   /* Allocate buff big enough to hold a section header,
02374      file header, or a.out header.  */
02375   {
02376     bfd_size_type siz;
02377 
02378     siz = scnhsz;
02379     if (siz < filhsz)
02380       siz = filhsz;
02381     if (siz < aoutsz)
02382       siz = aoutsz;
02383     buff = bfd_malloc (siz);
02384     if (buff == NULL)
02385       goto error_return;
02386   }
02387 
02388   internal_f.f_nscns = 0;
02389   if (bfd_seek (abfd, (file_ptr) (filhsz + aoutsz), SEEK_SET) != 0)
02390     goto error_return;
02391 
02392   for (current = abfd->sections;
02393        current != NULL;
02394        current = current->next)
02395     {
02396       struct internal_scnhdr section;
02397       bfd_vma vma;
02398 
02399       ++internal_f.f_nscns;
02400 
02401       strncpy (section.s_name, current->name, sizeof section.s_name);
02402 
02403       /* This seems to be correct for Irix 4 shared libraries.  */
02404       vma = bfd_get_section_vma (abfd, current);
02405       if (streq (current->name, _LIB))
02406        section.s_vaddr = 0;
02407       else
02408        section.s_vaddr = vma;
02409 
02410       section.s_paddr = current->lma;
02411       section.s_size = current->size;
02412 
02413       /* If this section is unloadable then the scnptr will be 0.  */
02414       if ((current->flags & (SEC_LOAD | SEC_HAS_CONTENTS)) == 0)
02415        section.s_scnptr = 0;
02416       else
02417        section.s_scnptr = current->filepos;
02418       section.s_relptr = current->rel_filepos;
02419 
02420       /* FIXME: the lnnoptr of the .sbss or .sdata section of an
02421         object file produced by the assembler is supposed to point to
02422         information about how much room is required by objects of
02423         various different sizes.  I think this only matters if we
02424         want the linker to compute the best size to use, or
02425         something.  I don't know what happens if the information is
02426         not present.  */
02427       if (! streq (current->name, _PDATA))
02428        section.s_lnnoptr = 0;
02429       else
02430        {
02431          /* The Alpha ECOFF .pdata section uses the lnnoptr field to
02432             hold the number of entries in the section (each entry is
02433             8 bytes).  We stored this in the line_filepos field in
02434             ecoff_compute_section_file_positions.  */
02435          section.s_lnnoptr = current->line_filepos;
02436        }
02437 
02438       section.s_nreloc = current->reloc_count;
02439       section.s_nlnno = 0;
02440       section.s_flags = ecoff_sec_to_styp_flags (current->name,
02441                                            current->flags);
02442 
02443       if (bfd_coff_swap_scnhdr_out (abfd, (void *) &section, buff) == 0
02444          || bfd_bwrite (buff, scnhsz, abfd) != scnhsz)
02445        goto error_return;
02446 
02447       if ((section.s_flags & STYP_TEXT) != 0
02448          || ((section.s_flags & STYP_RDATA) != 0
02449              && ecoff_data (abfd)->rdata_in_text)
02450          || section.s_flags == STYP_PDATA
02451          || (section.s_flags & STYP_DYNAMIC) != 0
02452          || (section.s_flags & STYP_LIBLIST) != 0
02453          || (section.s_flags & STYP_RELDYN) != 0
02454          || section.s_flags == STYP_CONFLIC
02455          || (section.s_flags & STYP_DYNSTR) != 0
02456          || (section.s_flags & STYP_DYNSYM) != 0
02457          || (section.s_flags & STYP_HASH) != 0
02458          || (section.s_flags & STYP_ECOFF_INIT) != 0
02459          || (section.s_flags & STYP_ECOFF_FINI) != 0
02460          || section.s_flags == STYP_RCONST)
02461        {
02462          text_size += current->size;
02463          if (! set_text_start || text_start > vma)
02464            {
02465              text_start = vma;
02466              set_text_start = TRUE;
02467            }
02468        }
02469       else if ((section.s_flags & STYP_RDATA) != 0
02470               || (section.s_flags & STYP_DATA) != 0
02471               || (section.s_flags & STYP_LITA) != 0
02472               || (section.s_flags & STYP_LIT8) != 0
02473               || (section.s_flags & STYP_LIT4) != 0
02474               || (section.s_flags & STYP_SDATA) != 0
02475               || section.s_flags == STYP_XDATA
02476               || (section.s_flags & STYP_GOT) != 0)
02477        {
02478          data_size += current->size;
02479          if (! set_data_start || data_start > vma)
02480            {
02481              data_start = vma;
02482              set_data_start = TRUE;
02483            }
02484        }
02485       else if ((section.s_flags & STYP_BSS) != 0
02486               || (section.s_flags & STYP_SBSS) != 0)
02487        bss_size += current->size;
02488       else if (section.s_flags == 0
02489               || (section.s_flags & STYP_ECOFF_LIB) != 0
02490               || section.s_flags == STYP_COMMENT)
02491        /* Do nothing.  */ ;
02492       else
02493        abort ();
02494     }
02495 
02496   /* Set up the file header.  */
02497   internal_f.f_magic = ecoff_get_magic (abfd);
02498 
02499   /* We will NOT put a fucking timestamp in the header here. Every
02500      time you put it back, I will come in and take it out again.  I'm
02501      sorry.  This field does not belong here.  We fill it with a 0 so
02502      it compares the same but is not a reasonable time. --
02503      gnu@cygnus.com.  */
02504   internal_f.f_timdat = 0;
02505 
02506   if (bfd_get_symcount (abfd) != 0)
02507     {
02508       /* The ECOFF f_nsyms field is not actually the number of
02509         symbols, it's the size of symbolic information header.  */
02510       internal_f.f_nsyms = external_hdr_size;
02511       internal_f.f_symptr = ecoff_data (abfd)->sym_filepos;
02512     }
02513   else
02514     {
02515       internal_f.f_nsyms = 0;
02516       internal_f.f_symptr = 0;
02517     }
02518 
02519   internal_f.f_opthdr = aoutsz;
02520 
02521   internal_f.f_flags = F_LNNO;
02522   if (reloc_size == 0)
02523     internal_f.f_flags |= F_RELFLG;
02524   if (bfd_get_symcount (abfd) == 0)
02525     internal_f.f_flags |= F_LSYMS;
02526   if (abfd->flags & EXEC_P)
02527     internal_f.f_flags |= F_EXEC;
02528 
02529   if (bfd_little_endian (abfd))
02530     internal_f.f_flags |= F_AR32WR;
02531   else
02532     internal_f.f_flags |= F_AR32W;
02533 
02534   /* Set up the ``optional'' header.  */
02535   if ((abfd->flags & D_PAGED) != 0)
02536     internal_a.magic = ECOFF_AOUT_ZMAGIC;
02537   else
02538     internal_a.magic = ECOFF_AOUT_OMAGIC;
02539 
02540   /* FIXME: Is this really correct?  */
02541   internal_a.vstamp = symhdr->vstamp;
02542 
02543   /* At least on Ultrix, these have to be rounded to page boundaries.
02544      FIXME: Is this true on other platforms?  */
02545   if ((abfd->flags & D_PAGED) != 0)
02546     {
02547       internal_a.tsize = (text_size + round - 1) &~ (round - 1);
02548       internal_a.text_start = text_start &~ (round - 1);
02549       internal_a.dsize = (data_size + round - 1) &~ (round - 1);
02550       internal_a.data_start = data_start &~ (round - 1);
02551     }
02552   else
02553     {
02554       internal_a.tsize = text_size;
02555       internal_a.text_start = text_start;
02556       internal_a.dsize = data_size;
02557       internal_a.data_start = data_start;
02558     }
02559 
02560   /* On Ultrix, the initial portions of the .sbss and .bss segments
02561      are at the end of the data section.  The bsize field in the
02562      optional header records how many bss bytes are required beyond
02563      those in the data section.  The value is not rounded to a page
02564      boundary.  */
02565   if (bss_size < internal_a.dsize - data_size)
02566     bss_size = 0;
02567   else
02568     bss_size -= internal_a.dsize - data_size;
02569   internal_a.bsize = bss_size;
02570   internal_a.bss_start = internal_a.data_start + internal_a.dsize;
02571 
02572   internal_a.entry = bfd_get_start_address (abfd);
02573 
02574   internal_a.gp_value = ecoff_data (abfd)->gp;
02575 
02576   internal_a.gprmask = ecoff_data (abfd)->gprmask;
02577   internal_a.fprmask = ecoff_data (abfd)->fprmask;
02578   for (i = 0; i < 4; i++)
02579     internal_a.cprmask[i] = ecoff_data (abfd)->cprmask[i];
02580 
02581   /* Let the backend adjust the headers if necessary.  */
02582   if (backend->adjust_headers)
02583     {
02584       if (! (*backend->adjust_headers) (abfd, &internal_f, &internal_a))
02585        goto error_return;
02586     }
02587 
02588   /* Write out the file header and the optional header.  */
02589   if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0)
02590     goto error_return;
02591 
02592   bfd_coff_swap_filehdr_out (abfd, (void *) &internal_f, buff);
02593   if (bfd_bwrite (buff, filhsz, abfd) != filhsz)
02594     goto error_return;
02595 
02596   bfd_coff_swap_aouthdr_out (abfd, (void *) &internal_a, buff);
02597   if (bfd_bwrite (buff, aoutsz, abfd) != aoutsz)
02598     goto error_return;
02599 
02600   /* Build the external symbol information.  This must be done before
02601      writing out the relocs so that we know the symbol indices.  We
02602      don't do this if this BFD was created by the backend linker,
02603      since it will have already handled the symbols and relocs.  */
02604   if (! ecoff_data (abfd)->linker)
02605     {
02606       symhdr->iextMax = 0;
02607       symhdr->issExtMax = 0;
02608       debug->external_ext = debug->external_ext_end = NULL;
02609       debug->ssext = debug->ssext_end = NULL;
02610       if (! bfd_ecoff_debug_externals (abfd, debug, &backend->debug_swap,
02611                                    (abfd->flags & EXEC_P) == 0,
02612                                    ecoff_get_extr, ecoff_set_index))
02613        goto error_return;
02614 
02615       /* Write out the relocs.  */
02616       for (current = abfd->sections;
02617           current != NULL;
02618           current = current->next)
02619        {
02620          arelent **reloc_ptr_ptr;
02621          arelent **reloc_end;
02622          char *out_ptr;
02623          bfd_size_type amt;
02624 
02625          if (current->reloc_count == 0)
02626            continue;
02627 
02628          amt = current->reloc_count * external_reloc_size;
02629          reloc_buff = bfd_alloc (abfd, amt);
02630          if (reloc_buff == NULL)
02631            goto error_return;
02632 
02633          reloc_ptr_ptr = current->orelocation;
02634          reloc_end = reloc_ptr_ptr + current->reloc_count;
02635          out_ptr = (char *) reloc_buff;
02636 
02637          for (;
02638               reloc_ptr_ptr < reloc_end;
02639               reloc_ptr_ptr++, out_ptr += external_reloc_size)
02640            {
02641              arelent *reloc;
02642              asymbol *sym;
02643              struct internal_reloc in;
02644 
02645              memset ((void *) &in, 0, sizeof in);
02646 
02647              reloc = *reloc_ptr_ptr;
02648              sym = *reloc->sym_ptr_ptr;
02649 
02650              /* If the howto field has not been initialised then skip this reloc.
02651                This assumes that an error message has been issued elsewhere.  */
02652              if (reloc->howto == NULL)
02653               continue;
02654 
02655              in.r_vaddr = (reloc->address
02656                          + bfd_get_section_vma (abfd, current));
02657              in.r_type = reloc->howto->type;
02658 
02659              if ((sym->flags & BSF_SECTION_SYM) == 0)
02660               {
02661                 in.r_symndx = ecoff_get_sym_index (*reloc->sym_ptr_ptr);
02662                 in.r_extern = 1;
02663               }
02664              else
02665               {
02666                 const char *name;
02667                 unsigned int i;
02668                 static struct
02669                 {
02670                   const char * name;
02671                   long r_symndx;
02672                 }
02673                 section_symndx [] =
02674                 {
02675                   { _TEXT,   RELOC_SECTION_TEXT   },
02676                   { _RDATA,  RELOC_SECTION_RDATA  },
02677                   { _DATA,   RELOC_SECTION_DATA   },
02678                   { _SDATA,  RELOC_SECTION_SDATA  },
02679                   { _SBSS,   RELOC_SECTION_SBSS   },
02680                   { _BSS,    RELOC_SECTION_BSS    },
02681                   { _INIT,   RELOC_SECTION_INIT   },
02682                   { _LIT8,   RELOC_SECTION_LIT8   },
02683                   { _LIT4,   RELOC_SECTION_LIT4   },
02684                   { _XDATA,  RELOC_SECTION_XDATA  },
02685                   { _PDATA,  RELOC_SECTION_PDATA  },
02686                   { _FINI,   RELOC_SECTION_FINI   },
02687                   { _LITA,   RELOC_SECTION_LITA   },
02688                   { "*ABS*", RELOC_SECTION_ABS    },
02689                   { _RCONST, RELOC_SECTION_RCONST }
02690                 };
02691 
02692                 name = bfd_get_section_name (abfd, bfd_get_section (sym));
02693 
02694                 for (i = 0; i < ARRAY_SIZE (section_symndx); i++)
02695                   if (streq (name, section_symndx[i].name))
02696                     {
02697                      in.r_symndx = section_symndx[i].r_symndx;
02698                      break;
02699                     }
02700 
02701                 if (i == ARRAY_SIZE (section_symndx))
02702                   abort ();
02703                 in.r_extern = 0;
02704               }
02705 
02706              (*adjust_reloc_out) (abfd, reloc, &in);
02707 
02708              (*swap_reloc_out) (abfd, &in, (void *) out_ptr);
02709            }
02710 
02711          if (bfd_seek (abfd, current->rel_filepos, SEEK_SET) != 0)
02712            goto error_return;
02713          amt = current->reloc_count * external_reloc_size;
02714          if (bfd_bwrite (reloc_buff, amt, abfd) != amt)
02715            goto error_return;
02716          bfd_release (abfd, reloc_buff);
02717          reloc_buff = NULL;
02718        }
02719 
02720       /* Write out the symbolic debugging information.  */
02721       if (bfd_get_symcount (abfd) > 0)
02722        {
02723          /* Write out the debugging information.  */
02724          if (! bfd_ecoff_write_debug (abfd, debug, &backend->debug_swap,
02725                                    ecoff_data (abfd)->sym_filepos))
02726            goto error_return;
02727        }
02728     }
02729 
02730   /* The .bss section of a demand paged executable must receive an
02731      entire page.  If there are symbols, the symbols will start on the
02732      next page.  If there are no symbols, we must fill out the page by
02733      hand.  */
02734   if (bfd_get_symcount (abfd) == 0
02735       && (abfd->flags & EXEC_P) != 0
02736       && (abfd->flags & D_PAGED) != 0)
02737     {
02738       char c;
02739 
02740       if (bfd_seek (abfd, (file_ptr) ecoff_data (abfd)->sym_filepos - 1,
02741                   SEEK_SET) != 0)
02742        goto error_return;
02743       if (bfd_bread (&c, (bfd_size_type) 1, abfd) == 0)
02744        c = 0;
02745       if (bfd_seek (abfd, (file_ptr) ecoff_data (abfd)->sym_filepos - 1,
02746                   SEEK_SET) != 0)
02747        goto error_return;
02748       if (bfd_bwrite (&c, (bfd_size_type) 1, abfd) != 1)
02749        goto error_return;
02750     }
02751 
02752   if (reloc_buff != NULL)
02753     bfd_release (abfd, reloc_buff);
02754   if (buff != NULL)
02755     free (buff);
02756   return TRUE;
02757  error_return:
02758   if (reloc_buff != NULL)
02759     bfd_release (abfd, reloc_buff);
02760   if (buff != NULL)
02761     free (buff);
02762   return FALSE;
02763 }
02764 
02765 /* Archive handling.  ECOFF uses what appears to be a unique type of
02766    archive header (armap).  The byte ordering of the armap and the
02767    contents are encoded in the name of the armap itself.  At least for
02768    now, we only support archives with the same byte ordering in the
02769    armap and the contents.
02770 
02771    The first four bytes in the armap are the number of symbol
02772    definitions.  This is always a power of two.
02773 
02774    This is followed by the symbol definitions.  Each symbol definition
02775    occupies 8 bytes.  The first four bytes are the offset from the
02776    start of the armap strings to the null-terminated string naming
02777    this symbol.  The second four bytes are the file offset to the
02778    archive member which defines this symbol.  If the second four bytes
02779    are 0, then this is not actually a symbol definition, and it should
02780    be ignored.
02781 
02782    The symbols are hashed into the armap with a closed hashing scheme.
02783    See the functions below for the details of the algorithm.
02784 
02785    After the symbol definitions comes four bytes holding the size of
02786    the string table, followed by the string table itself.  */
02787 
02788 /* The name of an archive headers looks like this:
02789    __________E[BL]E[BL]_ (with a trailing space).
02790    The trailing space is changed to an X if the archive is changed to
02791    indicate that the armap is out of date.
02792 
02793    The Alpha seems to use ________64E[BL]E[BL]_.  */
02794 
02795 #define ARMAP_BIG_ENDIAN           'B'
02796 #define ARMAP_LITTLE_ENDIAN               'L'
02797 #define ARMAP_MARKER                      'E'
02798 #define ARMAP_START_LENGTH         10
02799 #define ARMAP_HEADER_MARKER_INDEX  10
02800 #define ARMAP_HEADER_ENDIAN_INDEX  11
02801 #define ARMAP_OBJECT_MARKER_INDEX  12
02802 #define ARMAP_OBJECT_ENDIAN_INDEX  13
02803 #define ARMAP_END_INDEX            14
02804 #define ARMAP_END                  "_ "
02805 
02806 /* This is a magic number used in the hashing algorithm.  */
02807 #define ARMAP_HASH_MAGIC           0x9dd68ab5
02808 
02809 /* This returns the hash value to use for a string.  It also sets
02810    *REHASH to the rehash adjustment if the first slot is taken.  SIZE
02811    is the number of entries in the hash table, and HLOG is the log
02812    base 2 of SIZE.  */
02813 
02814 static unsigned int
02815 ecoff_armap_hash (const char *s,
02816                 unsigned int *rehash,
02817                 unsigned int size,
02818                 unsigned int hlog)
02819 {
02820   unsigned int hash;
02821 
02822   if (hlog == 0)
02823     return 0;
02824   hash = *s++;
02825   while (*s != '\0')
02826     hash = ((hash >> 27) | (hash << 5)) + *s++;
02827   hash *= ARMAP_HASH_MAGIC;
02828   *rehash = (hash & (size - 1)) | 1;
02829   return hash >> (32 - hlog);
02830 }
02831 
02832 /* Read in the armap.  */
02833 
02834 bfd_boolean
02835 _bfd_ecoff_slurp_armap (bfd *abfd)
02836 {
02837   char nextname[17];
02838   unsigned int i;
02839   struct areltdata *mapdata;
02840   bfd_size_type parsed_size;
02841   char *raw_armap;
02842   struct artdata *ardata;
02843   unsigned int count;
02844   char *raw_ptr;
02845   struct symdef *symdef_ptr;
02846   char *stringbase;
02847   bfd_size_type amt;
02848 
02849   /* Get the name of the first element.  */
02850   i = bfd_bread ((void *) nextname, (bfd_size_type) 16, abfd);
02851   if (i == 0)
02852       return TRUE;
02853   if (i != 16)
02854       return FALSE;
02855 
02856   if (bfd_seek (abfd, (file_ptr) -16, SEEK_CUR) != 0)
02857     return FALSE;
02858 
02859   /* Irix 4.0.5F apparently can use either an ECOFF armap or a
02860      standard COFF armap.  We could move the ECOFF armap stuff into
02861      bfd_slurp_armap, but that seems inappropriate since no other
02862      target uses this format.  Instead, we check directly for a COFF
02863      armap.  */
02864   if (CONST_STRNEQ (nextname, "/               "))
02865     return bfd_slurp_armap (abfd);
02866 
02867   /* See if the first element is an armap.  */
02868   if (! strneq (nextname, ecoff_backend (abfd)->armap_start, ARMAP_START_LENGTH)
02869       || nextname[ARMAP_HEADER_MARKER_INDEX] != ARMAP_MARKER
02870       || (nextname[ARMAP_HEADER_ENDIAN_INDEX] != ARMAP_BIG_ENDIAN
02871          && nextname[ARMAP_HEADER_ENDIAN_INDEX] != ARMAP_LITTLE_ENDIAN)
02872       || nextname[ARMAP_OBJECT_MARKER_INDEX] != ARMAP_MARKER
02873       || (nextname[ARMAP_OBJECT_ENDIAN_INDEX] != ARMAP_BIG_ENDIAN
02874          && nextname[ARMAP_OBJECT_ENDIAN_INDEX] != ARMAP_LITTLE_ENDIAN)
02875       || ! strneq (nextname + ARMAP_END_INDEX, ARMAP_END, sizeof ARMAP_END - 1))
02876     {
02877       bfd_has_map (abfd) = FALSE;
02878       return TRUE;
02879     }
02880 
02881   /* Make sure we have the right byte ordering.  */
02882   if (((nextname[ARMAP_HEADER_ENDIAN_INDEX] == ARMAP_BIG_ENDIAN)
02883        ^ (bfd_header_big_endian (abfd)))
02884       || ((nextname[ARMAP_OBJECT_ENDIAN_INDEX] == ARMAP_BIG_ENDIAN)
02885          ^ (bfd_big_endian (abfd))))
02886     {
02887       bfd_set_error (bfd_error_wrong_format);
02888       return FALSE;
02889     }
02890 
02891   /* Read in the armap.  */
02892   ardata = bfd_ardata (abfd);
02893   mapdata = (struct areltdata *) _bfd_read_ar_hdr (abfd);
02894   if (mapdata == NULL)
02895     return FALSE;
02896   parsed_size = mapdata->parsed_size;
02897   bfd_release (abfd, (void *) mapdata);
02898 
02899   raw_armap = bfd_alloc (abfd, parsed_size);
02900   if (raw_armap == NULL)
02901     return FALSE;
02902 
02903   if (bfd_bread ((void *) raw_armap, parsed_size, abfd) != parsed_size)
02904     {
02905       if (bfd_get_error () != bfd_error_system_call)
02906        bfd_set_error (bfd_error_malformed_archive);
02907       bfd_release (abfd, (void *) raw_armap);
02908       return FALSE;
02909     }
02910 
02911   ardata->tdata = (void *) raw_armap;
02912 
02913   count = H_GET_32 (abfd, raw_armap);
02914 
02915   ardata->symdef_count = 0;
02916   ardata->cache = NULL;
02917 
02918   /* This code used to overlay the symdefs over the raw archive data,
02919      but that doesn't work on a 64 bit host.  */
02920   stringbase = raw_armap + count * 8 + 8;
02921 
02922 #ifdef CHECK_ARMAP_HASH
02923   {
02924     unsigned int hlog;
02925 
02926     /* Double check that I have the hashing algorithm right by making
02927        sure that every symbol can be looked up successfully.  */
02928     hlog = 0;
02929     for (i = 1; i < count; i <<= 1)
02930       hlog++;
02931     BFD_ASSERT (i == count);
02932 
02933     raw_ptr = raw_armap + 4;
02934     for (i = 0; i < count; i++, raw_ptr += 8)
02935       {
02936        unsigned int name_offset, file_offset;
02937        unsigned int hash, rehash, srch;
02938 
02939        name_offset = H_GET_32 (abfd, raw_ptr);
02940        file_offset = H_GET_32 (abfd, (raw_ptr + 4));
02941        if (file_offset == 0)
02942          continue;
02943        hash = ecoff_armap_hash (stringbase + name_offset, &rehash, count,
02944                              hlog);
02945        if (hash == i)
02946          continue;
02947 
02948        /* See if we can rehash to this location.  */
02949        for (srch = (hash + rehash) & (count - 1);
02950             srch != hash && srch != i;
02951             srch = (srch + rehash) & (count - 1))
02952          BFD_ASSERT (H_GET_32 (abfd, (raw_armap + 8 + srch * 8)) != 0);
02953        BFD_ASSERT (srch == i);
02954       }
02955   }
02956 
02957 #endif /* CHECK_ARMAP_HASH */
02958 
02959   raw_ptr = raw_armap + 4;
02960   for (i = 0; i < count; i++, raw_ptr += 8)
02961     if (H_GET_32 (abfd, (raw_ptr + 4)) != 0)
02962       ++ardata->symdef_count;
02963 
02964   amt = ardata->symdef_count;
02965   amt *= sizeof (struct symdef);
02966   symdef_ptr = bfd_alloc (abfd, amt);
02967   if (!symdef_ptr)
02968     return FALSE;
02969 
02970   ardata->symdefs = (carsym *) symdef_ptr;
02971 
02972   raw_ptr = raw_armap + 4;
02973   for (i = 0; i < count; i++, raw_ptr += 8)
02974     {
02975       unsigned int name_offset, file_offset;
02976 
02977       file_offset = H_GET_32 (abfd, (raw_ptr + 4));
02978       if (file_offset == 0)
02979        continue;
02980       name_offset = H_GET_32 (abfd, raw_ptr);
02981       symdef_ptr->s.name = stringbase + name_offset;
02982       symdef_ptr->file_offset = file_offset;
02983       ++symdef_ptr;
02984     }
02985 
02986   ardata->first_file_filepos = bfd_tell (abfd);
02987   /* Pad to an even boundary.  */
02988   ardata->first_file_filepos += ardata->first_file_filepos % 2;
02989 
02990   bfd_has_map (abfd) = TRUE;
02991 
02992   return TRUE;
02993 }
02994 
02995 /* Write out an armap.  */
02996 
02997 bfd_boolean
02998 _bfd_ecoff_write_armap (bfd *abfd,
02999                      unsigned int elength,
03000                      struct orl *map,
03001                      unsigned int orl_count,
03002                      int stridx)
03003 {
03004   unsigned int hashsize, hashlog;
03005   bfd_size_type symdefsize;
03006   int padit;
03007   unsigned int stringsize;
03008   unsigned int mapsize;
03009   file_ptr firstreal;
03010   struct ar_hdr hdr;
03011   struct stat statbuf;
03012   unsigned int i;
03013   bfd_byte temp[4];
03014   bfd_byte *hashtable;
03015   bfd *current;
03016   bfd *last_elt;
03017 
03018   /* Ultrix appears to use as a hash table size the least power of two
03019      greater than twice the number of entries.  */
03020   for (hashlog = 0; ((unsigned int) 1 << hashlog) <= 2 * orl_count; hashlog++)
03021     ;
03022   hashsize = 1 << hashlog;
03023 
03024   symdefsize = hashsize * 8;
03025   padit = stridx % 2;
03026   stringsize = stridx + padit;
03027 
03028   /* Include 8 bytes to store symdefsize and stringsize in output.  */
03029   mapsize = symdefsize + stringsize + 8;
03030 
03031   firstreal = SARMAG + sizeof (struct ar_hdr) + mapsize + elength;
03032 
03033   memset ((void *) &hdr, 0, sizeof hdr);
03034 
03035   /* Work out the ECOFF armap name.  */
03036   strcpy (hdr.ar_name, ecoff_backend (abfd)->armap_start);
03037   hdr.ar_name[ARMAP_HEADER_MARKER_INDEX] = ARMAP_MARKER;
03038   hdr.ar_name[ARMAP_HEADER_ENDIAN_INDEX] =
03039     (bfd_header_big_endian (abfd)
03040      ? ARMAP_BIG_ENDIAN
03041      : ARMAP_LITTLE_ENDIAN);
03042   hdr.ar_name[ARMAP_OBJECT_MARKER_INDEX] = ARMAP_MARKER;
03043   hdr.ar_name[ARMAP_OBJECT_ENDIAN_INDEX] =
03044     bfd_big_endian (abfd) ? ARMAP_BIG_ENDIAN : ARMAP_LITTLE_ENDIAN;
03045   memcpy (hdr.ar_name + ARMAP_END_INDEX, ARMAP_END, sizeof ARMAP_END - 1);
03046 
03047   /* Write the timestamp of the archive header to be just a little bit
03048      later than the timestamp of the file, otherwise the linker will
03049      complain that the index is out of date.  Actually, the Ultrix
03050      linker just checks the archive name; the GNU linker may check the
03051      date.  */
03052   stat (abfd->filename, &statbuf);
03053   sprintf (hdr.ar_date, "%ld", (long) (statbuf.st_mtime + 60));
03054 
03055   /* The DECstation uses zeroes for the uid, gid and mode of the
03056      armap.  */
03057   hdr.ar_uid[0] = '0';
03058   hdr.ar_gid[0] = '0';
03059   /* Building gcc ends up extracting the armap as a file - twice.  */
03060   hdr.ar_mode[0] = '6';
03061   hdr.ar_mode[1] = '4';
03062   hdr.ar_mode[2] = '4';
03063 
03064   sprintf (hdr.ar_size, "%-10d", (int) mapsize);
03065 
03066   hdr.ar_fmag[0] = '`';
03067   hdr.ar_fmag[1] = '\012';
03068 
03069   /* Turn all null bytes in the header into spaces.  */
03070   for (i = 0; i < sizeof (struct ar_hdr); i++)
03071    if (((char *) (&hdr))[i] == '\0')
03072      (((char *) (&hdr))[i]) = ' ';
03073 
03074   if (bfd_bwrite ((void *) &hdr, (bfd_size_type) sizeof (struct ar_hdr), abfd)
03075       != sizeof (struct ar_hdr))
03076     return FALSE;
03077 
03078   H_PUT_32 (abfd, hashsize, temp);
03079   if (bfd_bwrite ((void *) temp, (bfd_size_type) 4, abfd) != 4)
03080     return FALSE;
03081 
03082   hashtable = bfd_zalloc (abfd, symdefsize);
03083   if (!hashtable)
03084     return FALSE;
03085 
03086   current = abfd->archive_head;
03087   last_elt = current;
03088   for (i = 0; i < orl_count; i++)
03089     {
03090       unsigned int hash, rehash;
03091 
03092       /* Advance firstreal to the file position of this archive
03093         element.  */
03094       if (map[i].u.abfd != last_elt)
03095        {
03096          do
03097            {
03098              firstreal += arelt_size (current) + sizeof (struct ar_hdr);
03099              firstreal += firstreal % 2;
03100              current = current->next;
03101            }
03102          while (current != map[i].u.abfd);
03103        }
03104 
03105       last_elt = current;
03106 
03107       hash = ecoff_armap_hash (*map[i].name, &rehash, hashsize, hashlog);
03108       if (H_GET_32 (abfd, (hashtable + (hash * 8) + 4)) != 0)
03109        {
03110          unsigned int srch;
03111 
03112          /* The desired slot is already taken.  */
03113          for (srch = (hash + rehash) & (hashsize - 1);
03114               srch != hash;
03115               srch = (srch + rehash) & (hashsize - 1))
03116            if (H_GET_32 (abfd, (hashtable + (srch * 8) + 4)) == 0)
03117              break;
03118 
03119          BFD_ASSERT (srch != hash);
03120 
03121          hash = srch;
03122        }
03123 
03124       H_PUT_32 (abfd, map[i].namidx, (hashtable + hash * 8));
03125       H_PUT_32 (abfd, firstreal, (hashtable + hash * 8 + 4));
03126     }
03127 
03128   if (bfd_bwrite ((void *) hashtable, symdefsize, abfd) != symdefsize)
03129     return FALSE;
03130 
03131   bfd_release (abfd, hashtable);
03132 
03133   /* Now write the strings.  */
03134   H_PUT_32 (abfd, stringsize, temp);
03135   if (bfd_bwrite ((void *) temp, (bfd_size_type) 4, abfd) != 4)
03136     return FALSE;
03137   for (i = 0; i < orl_count; i++)
03138     {
03139       bfd_size_type len;
03140 
03141       len = strlen (*map[i].name) + 1;
03142       if (bfd_bwrite ((void *) (*map[i].name), len, abfd) != len)
03143        return FALSE;
03144     }
03145 
03146   /* The spec sez this should be a newline.  But in order to be
03147      bug-compatible for DECstation ar we use a null.  */
03148   if (padit)
03149     {
03150       if (bfd_bwrite ("", (bfd_size_type) 1, abfd) != 1)
03151        return FALSE;
03152     }
03153 
03154   return TRUE;
03155 }
03156 
03157 /* See whether this BFD is an archive.  If it is, read in the armap
03158    and the extended name table.  */
03159 
03160 const bfd_target *
03161 _bfd_ecoff_archive_p (bfd *abfd)
03162 {
03163   struct artdata *tdata_hold;
03164   char armag[SARMAG + 1];
03165   bfd_size_type amt;
03166 
03167   if (bfd_bread ((void *) armag, (bfd_size_type) SARMAG, abfd) != SARMAG)
03168     {
03169       if (bfd_get_error () != bfd_error_system_call)
03170        bfd_set_error (bfd_error_wrong_format);
03171       return NULL;
03172     }
03173 
03174   if (! strneq (armag, ARMAG, SARMAG))
03175     {
03176       bfd_set_error (bfd_error_wrong_format);
03177       return NULL;
03178     }
03179 
03180   tdata_hold = bfd_ardata (abfd);
03181 
03182   amt = sizeof (struct artdata);
03183   bfd_ardata (abfd) = bfd_zalloc (abfd, amt);
03184   if (bfd_ardata (abfd) == NULL)
03185     {
03186       bfd_ardata (abfd) = tdata_hold;
03187       return NULL;
03188     }
03189 
03190   bfd_ardata (abfd)->first_file_filepos = SARMAG;
03191   /* Already cleared by bfd_zalloc above.
03192      bfd_ardata (abfd)->cache = NULL;
03193      bfd_ardata (abfd)->archive_head = NULL;
03194      bfd_ardata (abfd)->symdefs = NULL;
03195      bfd_ardata (abfd)->extended_names = NULL;
03196      bfd_ardata (abfd)->extended_names_size = 0;
03197      bfd_ardata (abfd)->tdata = NULL;  */
03198 
03199   if (! _bfd_ecoff_slurp_armap (abfd)
03200       || ! _bfd_ecoff_slurp_extended_name_table (abfd))
03201     {
03202       bfd_release (abfd, bfd_ardata (abfd));
03203       bfd_ardata (abfd) = tdata_hold;
03204       return NULL;
03205     }
03206 
03207   if (bfd_has_map (abfd))
03208     {
03209       bfd *first;
03210 
03211       /* This archive has a map, so we may presume that the contents
03212         are object files.  Make sure that if the first file in the
03213         archive can be recognized as an object file, it is for this
03214         target.  If not, assume that this is the wrong format.  If
03215         the first file is not an object file, somebody is doing
03216         something weird, and we permit it so that ar -t will work.  */
03217 
03218       first = bfd_openr_next_archived_file (abfd, NULL);
03219       if (first != NULL)
03220        {
03221          first->target_defaulted = FALSE;
03222          if (bfd_check_format (first, bfd_object)
03223              && first->xvec != abfd->xvec)
03224            {
03225              /* We ought to close `first' here, but we can't, because
03226                we have no way to remove it from the archive cache.
03227                It's almost impossible to figure out when we can
03228                release bfd_ardata.  FIXME.  */
03229              bfd_set_error (bfd_error_wrong_object_format);
03230              bfd_ardata (abfd) = tdata_hold;
03231              return NULL;
03232            }
03233          /* And we ought to close `first' here too.  */
03234        }
03235     }
03236 
03237   return abfd->xvec;
03238 }
03239 
03240 /* ECOFF linker code.  */
03241 
03242 /* Routine to create an entry in an ECOFF link hash table.  */
03243 
03244 static struct bfd_hash_entry *
03245 ecoff_link_hash_newfunc (struct bfd_hash_entry *entry,
03246                       struct bfd_hash_table *table,
03247                       const char *string)
03248 {
03249   struct ecoff_link_hash_entry *ret = (struct ecoff_link_hash_entry *) entry;
03250 
03251   /* Allocate the structure if it has not already been allocated by a
03252      subclass.  */
03253   if (ret == NULL)
03254     ret = ((struct ecoff_link_hash_entry *)
03255           bfd_hash_allocate (table, sizeof (struct ecoff_link_hash_entry)));
03256   if (ret == NULL)
03257     return NULL;
03258 
03259   /* Call the allocation method of the superclass.  */
03260   ret = ((struct ecoff_link_hash_entry *)
03261         _bfd_link_hash_newfunc ((struct bfd_hash_entry *) ret,
03262                              table, string));
03263 
03264   if (ret)
03265     {
03266       /* Set local fields.  */
03267       ret->indx = -1;
03268       ret->abfd = NULL;
03269       ret->written = 0;
03270       ret->small = 0;
03271     }
03272   memset ((void *) &ret->esym, 0, sizeof ret->esym);
03273 
03274   return (struct bfd_hash_entry *) ret;
03275 }
03276 
03277 /* Create an ECOFF link hash table.  */
03278 
03279 struct bfd_link_hash_table *
03280 _bfd_ecoff_bfd_link_hash_table_create (bfd *abfd)
03281 {
03282   struct ecoff_link_hash_table *ret;
03283   bfd_size_type amt = sizeof (struct ecoff_link_hash_table);
03284 
03285   ret = bfd_malloc (amt);
03286   if (ret == NULL)
03287     return NULL;
03288   if (!_bfd_link_hash_table_init (&ret->root, abfd,
03289                               ecoff_link_hash_newfunc,
03290                               sizeof (struct ecoff_link_hash_entry)))
03291     {
03292       free (ret);
03293       return NULL;
03294     }
03295   return &ret->root;
03296 }
03297 
03298 /* Look up an entry in an ECOFF link hash table.  */
03299 
03300 #define ecoff_link_hash_lookup(table, string, create, copy, follow) \
03301   ((struct ecoff_link_hash_entry *) \
03302    bfd_link_hash_lookup (&(table)->root, (string), (create), (copy), (follow)))
03303 
03304 /* Traverse an ECOFF link hash table.  */
03305 
03306 #define ecoff_link_hash_traverse(table, func, info)                   \
03307   (bfd_link_hash_traverse                                      \
03308    (&(table)->root,                                            \
03309     (bfd_boolean (*) (struct bfd_link_hash_entry *, void *)) (func),  \
03310     (info)))
03311 
03312 /* Get the ECOFF link hash table from the info structure.  This is
03313    just a cast.  */
03314 
03315 #define ecoff_hash_table(p) ((struct ecoff_link_hash_table *) ((p)->hash))
03316 
03317 /* Add the external symbols of an object file to the global linker
03318    hash table.  The external symbols and strings we are passed are
03319    just allocated on the stack, and will be discarded.  We must
03320    explicitly save any information we may need later on in the link.
03321    We do not want to read the external symbol information again.  */
03322 
03323 static bfd_boolean
03324 ecoff_link_add_externals (bfd *abfd,
03325                        struct bfd_link_info *info,
03326                        void * external_ext,
03327                        char *ssext)
03328 {
03329   const struct ecoff_backend_data * const backend = ecoff_backend (abfd);
03330   void (* const swap_ext_in) (bfd *, void *, EXTR *)
03331     = backend->debug_swap.swap_ext_in;
03332   bfd_size_type external_ext_size = backend->debug_swap.external_ext_size;
03333   unsigned long ext_count;
03334   struct bfd_link_hash_entry **sym_hash;
03335   char *ext_ptr;
03336   char *ext_end;
03337   bfd_size_type amt;
03338 
03339   ext_count = ecoff_data (abfd)->debug_info.symbolic_header.iextMax;
03340 
03341   amt = ext_count;
03342   amt *= sizeof (struct bfd_link_hash_entry *);
03343   sym_hash = bfd_alloc (abfd, amt);
03344   if (!sym_hash)
03345     return FALSE;
03346   ecoff_data (abfd)->sym_hashes = (struct ecoff_link_hash_entry **) sym_hash;
03347 
03348   ext_ptr = (char *) external_ext;
03349   ext_end = ext_ptr + ext_count * external_ext_size;
03350   for (; ext_ptr < ext_end; ext_ptr += external_ext_size, sym_hash++)
03351     {
03352       EXTR esym;
03353       bfd_boolean skip;
03354       bfd_vma value;
03355       asection *section;
03356       const char *name;
03357       struct ecoff_link_hash_entry *h;
03358 
03359       *sym_hash = NULL;
03360 
03361       (*swap_ext_in) (abfd, (void *) ext_ptr, &esym);
03362 
03363       /* Skip debugging symbols.  */
03364       skip = FALSE;
03365       switch (esym.asym.st)
03366        {
03367        case stGlobal:
03368        case stStatic:
03369        case stLabel:
03370        case stProc:
03371        case stStaticProc:
03372          break;
03373        default:
03374          skip = TRUE;
03375          break;
03376        }
03377 
03378       if (skip)
03379        continue;
03380 
03381       /* Get the information for this symbol.  */
03382       value = esym.asym.value;
03383       switch (esym.asym.sc)
03384        {
03385        default:
03386        case scNil:
03387        case scRegister:
03388        case scCdbLocal:
03389        case scBits:
03390        case scCdbSystem:
03391        case scRegImage:
03392        case scInfo:
03393        case scUserStruct:
03394        case scVar:
03395        case scVarRegister:
03396        case scVariant:
03397        case scBasedVar:
03398        case scXData:
03399        case scPData:
03400          section = NULL;
03401          break;
03402        case scText:
03403          section = bfd_make_section_old_way (abfd, _TEXT);
03404          value -= section->vma;
03405          break;
03406        case scData:
03407          section = bfd_make_section_old_way (abfd, _DATA);
03408          value -= section->vma;
03409          break;
03410        case scBss:
03411          section = bfd_make_section_old_way (abfd, _BSS);
03412          value -= section->vma;
03413          break;
03414        case scAbs:
03415          section = bfd_abs_section_ptr;
03416          break;
03417        case scUndefined:
03418          section = bfd_und_section_ptr;
03419          break;
03420        case scSData:
03421          section = bfd_make_section_old_way (abfd, _SDATA);
03422          value -= section->vma;
03423          break;
03424        case scSBss:
03425          section = bfd_make_section_old_way (abfd, _SBSS);
03426          value -= section->vma;
03427          break;
03428        case scRData:
03429          section = bfd_make_section_old_way (abfd, _RDATA);
03430          value -= section->vma;
03431          break;
03432        case scCommon:
03433          if (value > ecoff_data (abfd)->gp_size)
03434            {
03435              section = bfd_com_section_ptr;
03436              break;
03437            }
03438          /* Fall through.  */
03439        case scSCommon:
03440          if (ecoff_scom_section.name == NULL)
03441            {
03442              /* Initialize the small common section.  */
03443              ecoff_scom_section.name = SCOMMON;
03444              ecoff_scom_section.flags = SEC_IS_COMMON;
03445              ecoff_scom_section.output_section = &ecoff_scom_section;
03446              ecoff_scom_section.symbol = &ecoff_scom_symbol;
03447              ecoff_scom_section.symbol_ptr_ptr = &ecoff_scom_symbol_ptr;
03448              ecoff_scom_symbol.name = SCOMMON;
03449              ecoff_scom_symbol.flags = BSF_SECTION_SYM;
03450              ecoff_scom_symbol.section = &ecoff_scom_section;
03451              ecoff_scom_symbol_ptr = &ecoff_scom_symbol;
03452            }
03453          section = &ecoff_scom_section;
03454          break;
03455        case scSUndefined:
03456          section = bfd_und_section_ptr;
03457          break;
03458        case scInit:
03459          section = bfd_make_section_old_way (abfd, _INIT);
03460          value -= section->vma;
03461          break;
03462        case scFini:
03463          section = bfd_make_section_old_way (abfd, _FINI);
03464          value -= section->vma;
03465          break;
03466        case scRConst:
03467          section = bfd_make_section_old_way (abfd, _RCONST);
03468          value -= section->vma;
03469          break;
03470        }
03471 
03472       if (section == NULL)
03473        continue;
03474 
03475       name = ssext + esym.asym.iss;
03476 
03477       if (! (_bfd_generic_link_add_one_symbol
03478             (info, abfd, name,
03479              (flagword) (esym.weakext ? BSF_WEAK : BSF_GLOBAL),
03480              section, value, NULL, TRUE, TRUE, sym_hash)))
03481        return FALSE;
03482 
03483       h = (struct ecoff_link_hash_entry *) *sym_hash;
03484 
03485       /* If we are building an ECOFF hash table, save the external
03486         symbol information.  */
03487       if (info->hash->creator->flavour == bfd_get_flavour (abfd))
03488        {
03489          if (h->abfd == NULL
03490              || (! bfd_is_und_section (section)
03491                 && (! bfd_is_com_section (section)
03492                     || (h->root.type != bfd_link_hash_defined
03493                        && h->root.type != bfd_link_hash_defweak))))
03494            {
03495              h->abfd = abfd;
03496              h->esym = esym;
03497            }
03498 
03499          /* Remember whether this symbol was small undefined.  */
03500          if (esym.asym.sc == scSUndefined)
03501            h->small = 1;
03502 
03503          /* If this symbol was ever small undefined, it needs to wind
03504             up in a GP relative section.  We can't control the
03505             section of a defined symbol, but we can control the
03506             section of a common symbol.  This case is actually needed
03507             on Ultrix 4.2 to handle the symbol cred in -lckrb.  */
03508          if (h->small
03509              && h->root.type == bfd_link_hash_common
03510              && streq (h->root.u.c.p->section->name, SCOMMON))
03511            {
03512              h->root.u.c.p->section = bfd_make_section_old_way (abfd,
03513                                                          SCOMMON);
03514              h->root.u.c.p->section->flags = SEC_ALLOC;
03515              if (h->esym.asym.sc == scCommon)
03516               h->esym.asym.sc = scSCommon;
03517            }
03518        }
03519     }
03520 
03521   return TRUE;
03522 }
03523 
03524 /* Add symbols from an ECOFF object file to the global linker hash
03525    table.  */
03526 
03527 static bfd_boolean
03528 ecoff_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info)
03529 {
03530   HDRR *symhdr;
03531   bfd_size_type external_ext_size;
03532   void * external_ext = NULL;
03533   bfd_size_type esize;
03534   char *ssext = NULL;
03535   bfd_boolean result;
03536 
03537   if (! ecoff_slurp_symbolic_header (abfd))
03538     return FALSE;
03539 
03540   /* If there are no symbols, we don't want it.  */
03541   if (bfd_get_symcount (abfd) == 0)
03542     return TRUE;
03543 
03544   symhdr = &ecoff_data (abfd)->debug_info.symbolic_header;
03545 
03546   /* Read in the external symbols and external strings.  */
03547   external_ext_size = ecoff_backend (abfd)->debug_swap.external_ext_size;
03548   esize = symhdr->iextMax * external_ext_size;
03549   external_ext = bfd_malloc (esize);
03550   if (external_ext == NULL && esize != 0)
03551     goto error_return;
03552 
03553   if (bfd_seek (abfd, (file_ptr) symhdr->cbExtOffset, SEEK_SET) != 0
03554       || bfd_bread (external_ext, esize, abfd) != esize)
03555     goto error_return;
03556 
03557   ssext = bfd_malloc ((bfd_size_type) symhdr->issExtMax);
03558   if (ssext == NULL && symhdr->issExtMax != 0)
03559     goto error_return;
03560 
03561   if (bfd_seek (abfd, (file_ptr) symhdr->cbSsExtOffset, SEEK_SET) != 0
03562       || (bfd_bread (ssext, (bfd_size_type) symhdr->issExtMax, abfd)
03563          != (bfd_size_type) symhdr->issExtMax))
03564     goto error_return;
03565 
03566   result = ecoff_link_add_externals (abfd, info, external_ext, ssext);
03567 
03568   if (ssext != NULL)
03569     free (ssext);
03570   if (external_ext != NULL)
03571     free (external_ext);
03572   return result;
03573 
03574  error_return:
03575   if (ssext != NULL)
03576     free (ssext);
03577   if (external_ext != NULL)
03578     free (external_ext);
03579   return FALSE;
03580 }
03581 
03582 /* This is called if we used _bfd_generic_link_add_archive_symbols
03583    because we were not dealing with an ECOFF archive.  */
03584 
03585 static bfd_boolean
03586 ecoff_link_check_archive_element (bfd *abfd,
03587                               struct bfd_link_info *info,
03588                               bfd_boolean *pneeded)
03589 {
03590   const struct ecoff_backend_data * const backend = ecoff_backend (abfd);
03591   void (* const swap_ext_in) (bfd *, void *, EXTR *)
03592     = backend->debug_swap.swap_ext_in;
03593   HDRR *symhdr;
03594   bfd_size_type external_ext_size;
03595   void * external_ext = NULL;
03596   bfd_size_type esize;
03597   char *ssext = NULL;
03598   char *ext_ptr;
03599   char *ext_end;
03600 
03601   *pneeded = FALSE;
03602 
03603   if (! ecoff_slurp_symbolic_header (abfd))
03604     goto error_return;
03605 
03606   /* If there are no symbols, we don't want it.  */
03607   if (bfd_get_symcount (abfd) == 0)
03608     goto successful_return;
03609 
03610   symhdr = &ecoff_data (abfd)->debug_info.symbolic_header;
03611 
03612   /* Read in the external symbols and external strings.  */
03613   external_ext_size = backend->debug_swap.external_ext_size;
03614   esize = symhdr->iextMax * external_ext_size;
03615   external_ext = bfd_malloc (esize);
03616   if (external_ext == NULL && esize != 0)
03617     goto error_return;
03618 
03619   if (bfd_seek (abfd, (file_ptr) symhdr->cbExtOffset, SEEK_SET) != 0
03620       || bfd_bread (external_ext, esize, abfd) != esize)
03621     goto error_return;
03622 
03623   ssext = bfd_malloc ((bfd_size_type) symhdr->issExtMax);
03624   if (ssext == NULL && symhdr->issExtMax != 0)
03625     goto error_return;
03626 
03627   if (bfd_seek (abfd, (file_ptr) symhdr->cbSsExtOffset, SEEK_SET) != 0
03628       || (bfd_bread (ssext, (bfd_size_type) symhdr->issExtMax, abfd)
03629          != (bfd_size_type) symhdr->issExtMax))
03630     goto error_return;
03631 
03632   /* Look through the external symbols to see if they define some
03633      symbol that is currently undefined.  */
03634   ext_ptr = (char *) external_ext;
03635   ext_end = ext_ptr + esize;
03636   for (; ext_ptr < ext_end; ext_ptr += external_ext_size)
03637     {
03638       EXTR esym;
03639       bfd_boolean def;
03640       const char *name;
03641       struct bfd_link_hash_entry *h;
03642 
03643       (*swap_ext_in) (abfd, (void *) ext_ptr, &esym);
03644 
03645       /* See if this symbol defines something.  */
03646       if (esym.asym.st != stGlobal
03647          && esym.asym.st != stLabel
03648          && esym.asym.st != stProc)
03649        continue;
03650 
03651       switch (esym.asym.sc)
03652        {
03653        case scText:
03654        case scData:
03655        case scBss:
03656        case scAbs:
03657        case scSData:
03658        case scSBss:
03659        case scRData:
03660        case scCommon:
03661        case scSCommon:
03662        case scInit:
03663        case scFini:
03664        case scRConst:
03665          def = TRUE;
03666          break;
03667        default:
03668          def = FALSE;
03669          break;
03670        }
03671 
03672       if (! def)
03673        continue;
03674 
03675       name = ssext + esym.asym.iss;
03676       h = bfd_link_hash_lookup (info->hash, name, FALSE, FALSE, TRUE);
03677 
03678       /* Unlike the generic linker, we do not pull in elements because
03679         of common symbols.  */
03680       if (h == NULL
03681          || h->type != bfd_link_hash_undefined)
03682        continue;
03683 
03684       /* Include this element.  */
03685       if (! (*info->callbacks->add_archive_element) (info, abfd, name))
03686        goto error_return;
03687       if (! ecoff_link_add_externals (abfd, info, external_ext, ssext))
03688        goto error_return;
03689 
03690       *pneeded = TRUE;
03691       goto successful_return;
03692     }
03693 
03694  successful_return:
03695   if (external_ext != NULL)
03696     free (external_ext);
03697   if (ssext != NULL)
03698     free (ssext);
03699   return TRUE;
03700  error_return:
03701   if (external_ext != NULL)
03702     free (external_ext);
03703   if (ssext != NULL)
03704     free (ssext);
03705   return FALSE;
03706 }
03707 
03708 /* Add the symbols from an archive file to the global hash table.
03709    This looks through the undefined symbols, looks each one up in the
03710    archive hash table, and adds any associated object file.  We do not
03711    use _bfd_generic_link_add_archive_symbols because ECOFF archives
03712    already have a hash table, so there is no reason to construct
03713    another one.  */
03714 
03715 static bfd_boolean
03716 ecoff_link_add_archive_symbols (bfd *abfd, struct bfd_link_info *info)
03717 {
03718   const struct ecoff_backend_data * const backend = ecoff_backend (abfd);
03719   const bfd_byte *raw_armap;
03720   struct bfd_link_hash_entry **pundef;
03721   unsigned int armap_count;
03722   unsigned int armap_log;
03723   unsigned int i;
03724   const bfd_byte *hashtable;
03725   const char *stringbase;
03726 
03727   if (! bfd_has_map (abfd))
03728     {
03729       /* An empty archive is a special case.  */
03730       if (bfd_openr_next_archived_file (abfd, NULL) == NULL)
03731        return TRUE;
03732       bfd_set_error (bfd_error_no_armap);
03733       return FALSE;
03734     }
03735 
03736   /* If we don't have any raw data for this archive, as can happen on
03737      Irix 4.0.5F, we call the generic routine.
03738      FIXME: We should be more clever about this, since someday tdata
03739      may get to something for a generic archive.  */
03740   raw_armap = (const bfd_byte *) bfd_ardata (abfd)->tdata;
03741   if (raw_armap == NULL)
03742     return (_bfd_generic_link_add_archive_symbols
03743            (abfd, info, ecoff_link_check_archive_element));
03744 
03745   armap_count = H_GET_32 (abfd, raw_armap);
03746 
03747   armap_log = 0;
03748   for (i = 1; i < armap_count; i <<= 1)
03749     armap_log++;
03750   BFD_ASSERT (i == armap_count);
03751 
03752   hashtable = raw_armap + 4;
03753   stringbase = (const char *) raw_armap + armap_count * 8 + 8;
03754 
03755   /* Look through the list of undefined symbols.  */
03756   pundef = &info->hash->undefs;
03757   while (*pundef != NULL)
03758     {
03759       struct bfd_link_hash_entry *h;
03760       unsigned int hash, rehash;
03761       unsigned int file_offset;
03762       const char *name;
03763       bfd *element;
03764 
03765       h = *pundef;
03766 
03767       /* When a symbol is defined, it is not necessarily removed from
03768         the list.  */
03769       if (h->type != bfd_link_hash_undefined
03770          && h->type != bfd_link_hash_common)
03771        {
03772          /* Remove this entry from the list, for general cleanliness
03773             and because we are going to look through the list again
03774             if we search any more libraries.  We can't remove the
03775             entry if it is the tail, because that would lose any
03776             entries we add to the list later on.  */
03777          if (*pundef != info->hash->undefs_tail)
03778            *pundef = (*pundef)->u.undef.next;
03779          else
03780            pundef = &(*pundef)->u.undef.next;
03781          continue;
03782        }
03783 
03784       /* Native ECOFF linkers do not pull in archive elements merely
03785         to satisfy common definitions, so neither do we.  We leave
03786         them on the list, though, in case we are linking against some
03787         other object format.  */
03788       if (h->type != bfd_link_hash_undefined)
03789        {
03790          pundef = &(*pundef)->u.undef.next;
03791          continue;
03792        }
03793 
03794       /* Look for this symbol in the archive hash table.  */
03795       hash = ecoff_armap_hash (h->root.string, &rehash, armap_count,
03796                             armap_log);
03797 
03798       file_offset = H_GET_32 (abfd, hashtable + (hash * 8) + 4);
03799       if (file_offset == 0)
03800        {
03801          /* Nothing in this slot.  */
03802          pundef = &(*pundef)->u.undef.next;
03803          continue;
03804        }
03805 
03806       name = stringbase + H_GET_32 (abfd, hashtable + (hash * 8));
03807       if (name[0] != h->root.string[0]
03808          || ! streq (name, h->root.string))
03809        {
03810          unsigned int srch;
03811          bfd_boolean found;
03812 
03813          /* That was the wrong symbol.  Try rehashing.  */
03814          found = FALSE;
03815          for (srch = (hash + rehash) & (armap_count - 1);
03816               srch != hash;
03817               srch = (srch + rehash) & (armap_count - 1))
03818            {
03819              file_offset = H_GET_32 (abfd, hashtable + (srch * 8) + 4);
03820              if (file_offset == 0)
03821               break;
03822              name = stringbase + H_GET_32 (abfd, hashtable + (srch * 8));
03823              if (name[0] == h->root.string[0]
03824                 && streq (name, h->root.string))
03825               {
03826                 found = TRUE;
03827                 break;
03828               }
03829            }
03830 
03831          if (! found)
03832            {
03833              pundef = &(*pundef)->u.undef.next;
03834              continue;
03835            }
03836 
03837          hash = srch;
03838        }
03839 
03840       element = (*backend->get_elt_at_filepos) (abfd, (file_ptr) file_offset);
03841       if (element == NULL)
03842        return FALSE;
03843 
03844       if (! bfd_check_format (element, bfd_object))
03845        return FALSE;
03846 
03847       /* Unlike the generic linker, we know that this element provides
03848         a definition for an undefined symbol and we know that we want
03849         to include it.  We don't need to check anything.  */
03850       if (! (*info->callbacks->add_archive_element) (info, element, name))
03851        return FALSE;
03852       if (! ecoff_link_add_object_symbols (element, info))
03853        return FALSE;
03854 
03855       pundef = &(*pundef)->u.undef.next;
03856     }
03857 
03858   return TRUE;
03859 }
03860 
03861 /* Given an ECOFF BFD, add symbols to the global hash table as
03862    appropriate.  */
03863 
03864 bfd_boolean
03865 _bfd_ecoff_bfd_link_add_symbols (bfd *abfd, struct bfd_link_info *info)
03866 {
03867   switch (bfd_get_format (abfd))
03868     {
03869     case bfd_object:
03870       return ecoff_link_add_object_symbols (abfd, info);
03871     case bfd_archive:
03872       return ecoff_link_add_archive_symbols (abfd, info);
03873     default:
03874       bfd_set_error (bfd_error_wrong_format);
03875       return FALSE;
03876     }
03877 }
03878 
03879 
03880 /* ECOFF final link routines.  */
03881 
03882 /* Structure used to pass information to ecoff_link_write_external.  */
03883 
03884 struct extsym_info
03885 {
03886   bfd *abfd;
03887   struct bfd_link_info *info;
03888 };
03889 
03890 /* Accumulate the debugging information for an input BFD into the
03891    output BFD.  This must read in the symbolic information of the
03892    input BFD.  */
03893 
03894 static bfd_boolean
03895 ecoff_final_link_debug_accumulate (bfd *output_bfd,
03896                                bfd *input_bfd,
03897                                struct bfd_link_info *info,
03898                                void * handle)
03899 {
03900   struct ecoff_debug_info * const debug = &ecoff_data (input_bfd)->debug_info;
03901   const struct ecoff_debug_swap * const swap =
03902     &ecoff_backend (input_bfd)->debug_swap;
03903   HDRR *symhdr = &debug->symbolic_header;
03904   bfd_boolean ret;
03905 
03906 #define READ(ptr, offset, count, size, type)                           \
03907   if (symhdr->count == 0)                                       \
03908     debug->ptr = NULL;                                                 \
03909   else                                                          \
03910     {                                                           \
03911       bfd_size_type amt = (bfd_size_type) size * symhdr->count;               \
03912       debug->ptr = bfd_malloc (amt);                                   \
03913       if (debug->ptr == NULL)                                          \
03914        {                                                        \
03915           ret = FALSE;                                                 \
03916           goto return_something;                                \
03917        }                                                        \
03918       if (bfd_seek (input_bfd, (file_ptr) symhdr->offset, SEEK_SET) != 0 \
03919          || bfd_bread (debug->ptr, amt, input_bfd) != amt)             \
03920        {                                                        \
03921           ret = FALSE;                                                 \
03922           goto return_something;                                \
03923        }                                                        \
03924     }
03925 
03926   /* If raw_syments is not NULL, then the data was already by read by
03927      _bfd_ecoff_slurp_symbolic_info.  */
03928   if (ecoff_data (input_bfd)->raw_syments == NULL)
03929     {
03930       READ (line, cbLineOffset, cbLine, sizeof (unsigned char),
03931            unsigned char *);
03932       READ (external_dnr, cbDnOffset, idnMax, swap->external_dnr_size, void *);
03933       READ (external_pdr, cbPdOffset, ipdMax, swap->external_pdr_size, void *);
03934       READ (external_sym, cbSymOffset, isymMax, swap->external_sym_size, void *);
03935       READ (external_opt, cbOptOffset, ioptMax, swap->external_opt_size, void *);
03936       READ (external_aux, cbAuxOffset, iauxMax, sizeof (union aux_ext),
03937            union aux_ext *);
03938       READ (ss, cbSsOffset, issMax, sizeof (char), char *);
03939       READ (external_fdr, cbFdOffset, ifdMax, swap->external_fdr_size, void *);
03940       READ (external_rfd, cbRfdOffset, crfd, swap->external_rfd_size, void *);
03941     }
03942 #undef READ
03943 
03944   /* We do not read the external strings or the external symbols.  */
03945 
03946   ret = (bfd_ecoff_debug_accumulate
03947         (handle, output_bfd, &ecoff_data (output_bfd)->debug_info,
03948          &ecoff_backend (output_bfd)->debug_swap,
03949          input_bfd, debug, swap, info));
03950 
03951  return_something:
03952   if (ecoff_data (input_bfd)->raw_syments == NULL)
03953     {
03954       if (debug->line != NULL)
03955        free (debug->line);
03956       if (debug->external_dnr != NULL)
03957        free (debug->external_dnr);
03958       if (debug->external_pdr != NULL)
03959        free (debug->external_pdr);
03960       if (debug->external_sym != NULL)
03961        free (debug->external_sym);
03962       if (debug->external_opt != NULL)
03963        free (debug->external_opt);
03964       if (debug->external_aux != NULL)
03965        free (debug->external_aux);
03966       if (debug->ss != NULL)
03967        free (debug->ss);
03968       if (debug->external_fdr != NULL)
03969        free (debug->external_fdr);
03970       if (debug->external_rfd != NULL)
03971        free (debug->external_rfd);
03972 
03973       /* Make sure we don't accidentally follow one of these pointers
03974         into freed memory.  */
03975       debug->line = NULL;
03976       debug->external_dnr = NULL;
03977       debug->external_pdr = NULL;
03978       debug->external_sym = NULL;
03979       debug->external_opt = NULL;
03980       debug->external_aux = NULL;
03981       debug->ss = NULL;
03982       debug->external_fdr = NULL;
03983       debug->external_rfd = NULL;
03984     }
03985 
03986   return ret;
03987 }
03988 
03989 /* Relocate and write an ECOFF section into an ECOFF output file.  */
03990 
03991 static bfd_boolean
03992 ecoff_indirect_link_order (bfd *output_bfd,
03993                         struct bfd_link_info *info,
03994                         asection *output_section,
03995                         struct bfd_link_order *link_order)
03996 {
03997   asection *input_section;
03998   bfd *input_bfd;
03999   bfd_byte *contents = NULL;
04000   bfd_size_type external_reloc_size;
04001   bfd_size_type external_relocs_size;
04002   void * external_relocs = NULL;
04003 
04004   BFD_ASSERT ((output_section->flags & SEC_HAS_CONTENTS) != 0);
04005 
04006   input_section = link_order->u.indirect.section;
04007   input_bfd = input_section->owner;
04008   if (input_section->size == 0)
04009     return TRUE;
04010 
04011   BFD_ASSERT (input_section->output_section == output_section);
04012   BFD_ASSERT (input_section->output_offset == link_order->offset);
04013   BFD_ASSERT (input_section->size == link_order->size);
04014 
04015   /* Get the section contents.  */
04016   if (!bfd_malloc_and_get_section (input_bfd, input_section, &contents))
04017     goto error_return;
04018 
04019   /* Get the relocs.  If we are relaxing MIPS code, they will already
04020      have been read in.  Otherwise, we read them in now.  */
04021   external_reloc_size = ecoff_backend (input_bfd)->external_reloc_size;
04022   external_relocs_size = external_reloc_size * input_section->reloc_count;
04023 
04024   external_relocs = bfd_malloc (external_relocs_size);
04025   if (external_relocs == NULL && external_relocs_size != 0)
04026     goto error_return;
04027 
04028   if (bfd_seek (input_bfd, input_section->rel_filepos, SEEK_SET) != 0
04029       || (bfd_bread (external_relocs, external_relocs_size, input_bfd)
04030          != external_relocs_size))
04031     goto error_return;
04032 
04033   /* Relocate the section contents.  */
04034   if (! ((*ecoff_backend (input_bfd)->relocate_section)
04035         (output_bfd, info, input_bfd, input_section, contents,
04036          external_relocs)))
04037     goto error_return;
04038 
04039   /* Write out the relocated section.  */
04040   if (! bfd_set_section_contents (output_bfd,
04041                               output_section,
04042                               contents,
04043                               input_section->output_offset,
04044                               input_section->size))
04045     goto error_return;
04046 
04047   /* If we are producing relocatable output, the relocs were
04048      modified, and we write them out now.  We use the reloc_count
04049      field of output_section to keep track of the number of relocs we
04050      have output so far.  */
04051   if (info->relocatable)
04052     {
04053       file_ptr pos = (output_section->rel_filepos
04054                     + output_section->reloc_count * external_reloc_size);
04055       if (bfd_seek (output_bfd, pos, SEEK_SET) != 0
04056          || (bfd_bwrite (external_relocs, external_relocs_size, output_bfd)
04057              != external_relocs_size))
04058        goto error_return;
04059       output_section->reloc_count += input_section->reloc_count;
04060     }
04061 
04062   if (contents != NULL)
04063     free (contents);
04064   if (external_relocs != NULL)
04065     free (external_relocs);
04066   return TRUE;
04067 
04068  error_return:
04069   if (contents != NULL)
04070     free (contents);
04071   if (external_relocs != NULL)
04072     free (external_relocs);
04073   return FALSE;
04074 }
04075 
04076 /* Generate a reloc when linking an ECOFF file.  This is a reloc
04077    requested by the linker, and does come from any input file.  This
04078    is used to build constructor and destructor tables when linking
04079    with -Ur.  */
04080 
04081 static bfd_boolean
04082 ecoff_reloc_link_order (bfd *output_bfd,
04083                      struct bfd_link_info *info,
04084                      asection *output_section,
04085                      struct bfd_link_order *link_order)
04086 {
04087   enum bfd_link_order_type type;
04088   asection *section;
04089   bfd_vma addend;
04090   arelent rel;
04091   struct internal_reloc in;
04092   bfd_size_type external_reloc_size;
04093   bfd_byte *rbuf;
04094   bfd_boolean ok;
04095   file_ptr pos;
04096 
04097   type = link_order->type;
04098   section = NULL;
04099   addend = link_order->u.reloc.p->addend;
04100 
04101   /* We set up an arelent to pass to the backend adjust_reloc_out
04102      routine.  */
04103   rel.address = link_order->offset;
04104 
04105   rel.howto = bfd_reloc_type_lookup (output_bfd, link_order->u.reloc.p->reloc);
04106   if (rel.howto == 0)
04107     {
04108       bfd_set_error (bfd_error_bad_value);
04109       return FALSE;
04110     }
04111 
04112   if (type == bfd_section_reloc_link_order)
04113     {
04114       section = link_order->u.reloc.p->u.section;
04115       rel.sym_ptr_ptr = section->symbol_ptr_ptr;
04116     }
04117   else
04118     {
04119       struct bfd_link_hash_entry *h;
04120 
04121       /* Treat a reloc against a defined symbol as though it were
04122          actually against the section.  */
04123       h = bfd_wrapped_link_hash_lookup (output_bfd, info,
04124                                    link_order->u.reloc.p->u.name,
04125                                    FALSE, FALSE, FALSE);
04126       if (h != NULL
04127          && (h->type == bfd_link_hash_defined
04128              || h->type == bfd_link_hash_defweak))
04129        {
04130          type = bfd_section_reloc_link_order;
04131          section = h->u.def.section->output_section;
04132          /* It seems that we ought to add the symbol value to the
04133              addend here, but in practice it has already been added
04134              because it was passed to constructor_callback.  */
04135          addend += section->vma + h->u.def.section->output_offset;
04136        }
04137       else
04138        {
04139          /* We can't set up a reloc against a symbol correctly,
04140             because we have no asymbol structure.  Currently no
04141             adjust_reloc_out routine cares.  */
04142          rel.sym_ptr_ptr = NULL;
04143        }
04144     }
04145 
04146   /* All ECOFF relocs are in-place.  Put the addend into the object
04147      file.  */
04148 
04149   BFD_ASSERT (rel.howto->partial_inplace);
04150   if (addend != 0)
04151     {
04152       bfd_size_type size;
04153       bfd_reloc_status_type rstat;
04154       bfd_byte *buf;
04155 
04156       size = bfd_get_reloc_size (rel.howto);
04157       buf = bfd_zmalloc (size);
04158       if (buf == NULL)
04159        return FALSE;
04160       rstat = _bfd_relocate_contents (rel.howto, output_bfd,
04161                                   (bfd_vma) addend, buf);
04162       switch (rstat)
04163        {
04164        case bfd_reloc_ok:
04165          break;
04166        default:
04167        case bfd_reloc_outofrange:
04168          abort ();
04169        case bfd_reloc_overflow:
04170          if (! ((*info->callbacks->reloc_overflow)
04171                (info, NULL,
04172                 (link_order->type == bfd_section_reloc_link_order
04173                  ? bfd_section_name (output_bfd, section)
04174                  : link_order->u.reloc.p->u.name),
04175                 rel.howto->name, addend, NULL,
04176                 NULL, (bfd_vma) 0)))
04177            {
04178              free (buf);
04179              return FALSE;
04180            }
04181          break;
04182        }
04183       ok = bfd_set_section_contents (output_bfd, output_section, (void *) buf,
04184                                  (file_ptr) link_order->offset, size);
04185       free (buf);
04186       if (! ok)
04187        return FALSE;
04188     }
04189 
04190   rel.addend = 0;
04191 
04192   /* Move the information into an internal_reloc structure.  */
04193   in.r_vaddr = (rel.address
04194               + bfd_get_section_vma (output_bfd, output_section));
04195   in.r_type = rel.howto->type;
04196 
04197   if (type == bfd_symbol_reloc_link_order)
04198     {
04199       struct ecoff_link_hash_entry *h;
04200 
04201       h = ((struct ecoff_link_hash_entry *)
04202           bfd_wrapped_link_hash_lookup (output_bfd, info,
04203                                     link_order->u.reloc.p->u.name,
04204                                     FALSE, FALSE, TRUE));
04205       if (h != NULL
04206          && h->indx != -1)
04207        in.r_symndx = h->indx;
04208       else
04209        {
04210          if (! ((*info->callbacks->unattached_reloc)
04211                (info, link_order->u.reloc.p->u.name, NULL,
04212                 NULL, (bfd_vma) 0)))
04213            return FALSE;
04214          in.r_symndx = 0;
04215        }
04216       in.r_extern = 1;
04217     }
04218   else
04219     {
04220       const char *name;
04221       unsigned int i;
04222       static struct
04223       {
04224        const char * name;
04225        long r_symndx;
04226       }
04227       section_symndx [] =
04228       {
04229        { _TEXT,   RELOC_SECTION_TEXT   },
04230        { _RDATA,  RELOC_SECTION_RDATA  },
04231        { _DATA,   RELOC_SECTION_DATA   },
04232        { _SDATA,  RELOC_SECTION_SDATA  },
04233        { _SBSS,   RELOC_SECTION_SBSS   },
04234        { _BSS,    RELOC_SECTION_BSS    },
04235        { _INIT,   RELOC_SECTION_INIT   },
04236        { _LIT8,   RELOC_SECTION_LIT8   },
04237        { _LIT4,   RELOC_SECTION_LIT4   },
04238        { _XDATA,  RELOC_SECTION_XDATA  },
04239        { _PDATA,  RELOC_SECTION_PDATA  },
04240        { _FINI,   RELOC_SECTION_FINI   },
04241        { _LITA,   RELOC_SECTION_LITA   },
04242        { "*ABS*", RELOC_SECTION_ABS    },
04243        { _RCONST, RELOC_SECTION_RCONST }
04244       };
04245 
04246       name = bfd_get_section_name (output_bfd, section);
04247 
04248       for (i = 0; i < ARRAY_SIZE (section_symndx); i++)
04249        if (streq (name, section_symndx[i].name))
04250          {
04251            in.r_symndx = section_symndx[i].r_symndx;
04252            break;
04253          }
04254 
04255       if (i == ARRAY_SIZE (section_symndx))
04256        abort ();
04257 
04258       in.r_extern = 0;
04259     }
04260 
04261   /* Let the BFD backend adjust the reloc.  */
04262   (*ecoff_backend (output_bfd)->adjust_reloc_out) (output_bfd, &rel, &in);
04263 
04264   /* Get some memory and swap out the reloc.  */
04265   external_reloc_size = ecoff_backend (output_bfd)->external_reloc_size;
04266   rbuf = bfd_malloc (external_reloc_size);
04267   if (rbuf == NULL)
04268     return FALSE;
04269 
04270   (*ecoff_backend (output_bfd)->swap_reloc_out) (output_bfd, &in, (void *) rbuf);
04271 
04272   pos = (output_section->rel_filepos
04273         + output_section->reloc_count * external_reloc_size);
04274   ok = (bfd_seek (output_bfd, pos, SEEK_SET) == 0
04275        && (bfd_bwrite ((void *) rbuf, external_reloc_size, output_bfd)
04276            == external_reloc_size));
04277 
04278   if (ok)
04279     ++output_section->reloc_count;
04280 
04281   free (rbuf);
04282 
04283   return ok;
04284 }
04285 
04286 /* Put out information for an external symbol.  These come only from
04287    the hash table.  */
04288 
04289 static bfd_boolean
04290 ecoff_link_write_external (struct ecoff_link_hash_entry *h, void * data)
04291 {
04292   struct extsym_info *einfo = (struct extsym_info *) data;
04293   bfd *output_bfd = einfo->abfd;
04294   bfd_boolean strip;
04295 
04296   if (h->root.type == bfd_link_hash_warning)
04297     {
04298       h = (struct ecoff_link_hash_entry *) h->root.u.i.link;
04299       if (h->root.type == bfd_link_hash_new)
04300        return TRUE;
04301     }
04302 
04303   /* We need to check if this symbol is being stripped.  */
04304   if (h->root.type == bfd_link_hash_undefined
04305       || h->root.type == bfd_link_hash_undefweak)
04306     strip = FALSE;
04307   else if (einfo->info->strip == strip_all
04308           || (einfo->info->strip == strip_some
04309               && bfd_hash_lookup (einfo->info->keep_hash,
04310                                h->root.root.string,
04311                                FALSE, FALSE) == NULL))
04312     strip = TRUE;
04313   else
04314     strip = FALSE;
04315 
04316   if (strip || h->written)
04317     return TRUE;
04318 
04319   if (h->abfd == NULL)
04320     {
04321       h->esym.jmptbl = 0;
04322       h->esym.cobol_main = 0;
04323       h->esym.weakext = 0;
04324       h->esym.reserved = 0;
04325       h->esym.ifd = ifdNil;
04326       h->esym.asym.value = 0;
04327       h->esym.asym.st = stGlobal;
04328 
04329       if (h->root.type != bfd_link_hash_defined
04330          && h->root.type != bfd_link_hash_defweak)
04331        h->esym.asym.sc = scAbs;
04332       else
04333        {
04334          asection *output_section;
04335          const char *name;
04336          unsigned int i;
04337          static struct
04338          {
04339            const char * name;
04340            int sc;
04341          }
04342          section_storage_classes [] =
04343          {
04344            { _TEXT,   scText   },
04345            { _DATA,   scData   },
04346            { _SDATA,  scSData  },
04347            { _RDATA,  scRData  },
04348            { _BSS,    scBss    },
04349            { _SBSS,   scSBss   },
04350            { _INIT,   scInit   },
04351            { _FINI,   scFini   },
04352            { _PDATA,  scPData  },
04353            { _XDATA,  scXData  },
04354            { _RCONST, scRConst }
04355          };
04356 
04357          output_section = h->root.u.def.section->output_section;
04358          name = bfd_section_name (output_section->owner, output_section);
04359 
04360          for (i = 0; i < ARRAY_SIZE (section_storage_classes); i++)
04361            if (streq (name, section_storage_classes[i].name))
04362              {
04363               h->esym.asym.sc = section_storage_classes[i].sc;
04364               break;
04365              }
04366 
04367          if (i == ARRAY_SIZE (section_storage_classes))
04368            h->esym.asym.sc = scAbs;
04369        }
04370 
04371       h->esym.asym.reserved = 0;
04372       h->esym.asym.index = indexNil;
04373     }
04374   else if (h->esym.ifd != -1)
04375     {
04376       struct ecoff_debug_info *debug;
04377 
04378       /* Adjust the FDR index for the symbol by that used for the
04379         input BFD.  */
04380       debug = &ecoff_data (h->abfd)->debug_info;
04381       BFD_ASSERT (h->esym.ifd >= 0
04382                 && h->esym.ifd < debug->symbolic_header.ifdMax);
04383       h->esym.ifd = debug->ifdmap[h->esym.ifd];
04384     }
04385 
04386   switch (h->root.type)
04387     {
04388     default:
04389     case bfd_link_hash_warning:
04390     case bfd_link_hash_new:
04391       abort ();
04392     case bfd_link_hash_undefined:
04393     case bfd_link_hash_undefweak:
04394       if (h->esym.asym.sc != scUndefined
04395          && h->esym.asym.sc != scSUndefined)
04396        h->esym.asym.sc = scUndefined;
04397       break;
04398     case bfd_link_hash_defined:
04399     case bfd_link_hash_defweak:
04400       if (h->esym.asym.sc == scUndefined
04401          || h->esym.asym.sc == scSUndefined)
04402        h->esym.asym.sc = scAbs;
04403       else if (h->esym.asym.sc == scCommon)
04404        h->esym.asym.sc = scBss;
04405       else if (h->esym.asym.sc == scSCommon)
04406        h->esym.asym.sc = scSBss;
04407       h->esym.asym.value = (h->root.u.def.value
04408                          + h->root.u.def.section->output_section->vma
04409                          + h->root.u.def.section->output_offset);
04410       break;
04411     case bfd_link_hash_common:
04412       if (h->esym.asym.sc != scCommon
04413          && h->esym.asym.sc != scSCommon)
04414        h->esym.asym.sc = scCommon;
04415       h->esym.asym.value = h->root.u.c.size;
04416       break;
04417     case bfd_link_hash_indirect:
04418       /* We ignore these symbols, since the indirected symbol is
04419         already in the hash table.  */
04420       return TRUE;
04421     }
04422 
04423   /* bfd_ecoff_debug_one_external uses iextMax to keep track of the
04424      symbol number.  */
04425   h->indx = ecoff_data (output_bfd)->debug_info.symbolic_header.iextMax;
04426   h->written = 1;
04427 
04428   return (bfd_ecoff_debug_one_external
04429          (output_bfd, &ecoff_data (output_bfd)->debug_info,
04430           &ecoff_backend (output_bfd)->debug_swap, h->root.root.string,
04431           &h->esym));
04432 }
04433 
04434 /* ECOFF final link routine.  This looks through all the input BFDs
04435    and gathers together all the debugging information, and then
04436    processes all the link order information.  This may cause it to
04437    close and reopen some input BFDs; I'll see how bad this is.  */
04438 
04439 bfd_boolean
04440 _bfd_ecoff_bfd_final_link (bfd *abfd, struct bfd_link_info *info)
04441 {
04442   const struct ecoff_backend_data * const backend = ecoff_backend (abfd);
04443   struct ecoff_debug_info * const debug = &ecoff_data (abfd)->debug_info;
04444   HDRR *symhdr;
04445   void * handle;
04446   bfd *input_bfd;
04447   asection *o;
04448   struct bfd_link_order *p;
04449   struct extsym_info einfo;
04450 
04451   /* We accumulate the debugging information counts in the symbolic
04452      header.  */
04453   symhdr = &debug->symbolic_header;
04454   symhdr->vstamp = 0;
04455   symhdr->ilineMax = 0;
04456   symhdr->cbLine = 0;
04457   symhdr->idnMax = 0;
04458   symhdr->ipdMax = 0;
04459   symhdr->isymMax = 0;
04460   symhdr->ioptMax = 0;
04461   symhdr->iauxMax = 0;
04462   symhdr->issMax = 0;
04463   symhdr->issExtMax = 0;
04464   symhdr->ifdMax = 0;
04465   symhdr->crfd = 0;
04466   symhdr->iextMax = 0;
04467 
04468   /* We accumulate the debugging information itself in the debug_info
04469      structure.  */
04470   debug->line = NULL;
04471   debug->external_dnr = NULL;
04472   debug->external_pdr = NULL;
04473   debug->external_sym = NULL;
04474   debug->external_opt = NULL;
04475   debug->external_aux = NULL;
04476   debug->ss = NULL;
04477   debug->ssext = debug->ssext_end = NULL;
04478   debug->external_fdr = NULL;
04479   debug->external_rfd = NULL;
04480   debug->external_ext = debug->external_ext_end = NULL;
04481 
04482   handle = bfd_ecoff_debug_init (abfd, debug, &backend->debug_swap, info);
04483   if (handle == NULL)
04484     return FALSE;
04485 
04486   /* Accumulate the debugging symbols from each input BFD.  */
04487   for (input_bfd = info->input_bfds;
04488        input_bfd != NULL;
04489        input_bfd = input_bfd->link_next)
04490     {
04491       bfd_boolean ret;
04492 
04493       if (bfd_get_flavour (input_bfd) == bfd_target_ecoff_flavour)
04494        {
04495          /* Arbitrarily set the symbolic header vstamp to the vstamp
04496             of the first object file in the link.  */
04497          if (symhdr->vstamp == 0)
04498            symhdr->vstamp
04499              = ecoff_data (input_bfd)->debug_info.symbolic_header.vstamp;
04500          ret = ecoff_final_link_debug_accumulate (abfd, input_bfd, info,
04501                                              handle);
04502        }
04503       else
04504        ret = bfd_ecoff_debug_accumulate_other (handle, abfd,
04505                                           debug, &backend->debug_swap,
04506                                           input_bfd, info);
04507       if (! ret)
04508        return FALSE;
04509 
04510       /* Combine the register masks.  */
04511       ecoff_data (abfd)->gprmask |= ecoff_data (input_bfd)->gprmask;
04512       ecoff_data (abfd)->fprmask |= ecoff_data (input_bfd)->fprmask;
04513       ecoff_data (abfd)->cprmask[0] |= ecoff_data (input_bfd)->cprmask[0];
04514       ecoff_data (abfd)->cprmask[1] |= ecoff_data (input_bfd)->cprmask[1];
04515       ecoff_data (abfd)->cprmask[2] |= ecoff_data (input_bfd)->cprmask[2];
04516       ecoff_data (abfd)->cprmask[3] |= ecoff_data (input_bfd)->cprmask[3];
04517     }
04518 
04519   /* Write out the external symbols.  */
04520   einfo.abfd = abfd;
04521   einfo.info = info;
04522   ecoff_link_hash_traverse (ecoff_hash_table (info),
04523                          ecoff_link_write_external,
04524                          (void *) &einfo);
04525 
04526   if (info->relocatable)
04527     {
04528       /* We need to make a pass over the link_orders to count up the
04529         number of relocations we will need to output, so that we know
04530         how much space they will take up.  */
04531       for (o = abfd->sections; o != NULL; o = o->next)
04532        {
04533          o->reloc_count = 0;
04534          for (p = o->map_head.link_order;
04535               p != NULL;
04536               p = p->next)
04537            if (p->type == bfd_indirect_link_order)
04538              o->reloc_count += p->u.indirect.section->reloc_count;
04539            else if (p->type == bfd_section_reloc_link_order
04540                    || p->type == bfd_symbol_reloc_link_order)
04541              ++o->reloc_count;
04542        }
04543     }
04544 
04545   /* Compute the reloc and symbol file positions.  */
04546   ecoff_compute_reloc_file_positions (abfd);
04547 
04548   /* Write out the debugging information.  */
04549   if (! bfd_ecoff_write_accumulated_debug (handle, abfd, debug,
04550                                       &backend->debug_swap, info,
04551                                       ecoff_data (abfd)->sym_filepos))
04552     return FALSE;
04553 
04554   bfd_ecoff_debug_free (handle, abfd, debug, &backend->debug_swap, info);
04555 
04556   if (info->relocatable)
04557     {
04558       /* Now reset the reloc_count field of the sections in the output
04559         BFD to 0, so that we can use them to keep track of how many
04560         relocs we have output thus far.  */
04561       for (o = abfd->sections; o != NULL; o = o->next)
04562        o->reloc_count = 0;
04563     }
04564 
04565   /* Get a value for the GP register.  */
04566   if (ecoff_data (abfd)->gp == 0)
04567     {
04568       struct bfd_link_hash_entry *h;
04569 
04570       h = bfd_link_hash_lookup (info->hash, "_gp", FALSE, FALSE, TRUE);
04571       if (h != NULL
04572          && h->type == bfd_link_hash_defined)
04573        ecoff_data (abfd)->gp = (h->u.def.value
04574                              + h->u.def.section->output_section->vma
04575                              + h->u.def.section->output_offset);
04576       else if (info->relocatable)
04577        {
04578          bfd_vma lo;
04579 
04580          /* Make up a value.  */
04581          lo = (bfd_vma) -1;
04582          for (o = abfd->sections; o != NULL; o = o->next)
04583            {
04584              if (o->vma < lo
04585                 && (streq (o->name, _SBSS)
04586                     || streq (o->name, _SDATA)
04587                     || streq (o->name, _LIT4)
04588                     || streq (o->name, _LIT8)
04589                     || streq (o->name, _LITA)))
04590               lo = o->vma;
04591            }
04592          ecoff_data (abfd)->gp = lo + 0x8000;
04593        }
04594       else
04595        {
04596          /* If the relocate_section function needs to do a reloc
04597             involving the GP value, it should make a reloc_dangerous
04598             callback to warn that GP is not defined.  */
04599        }
04600     }
04601 
04602   for (o = abfd->sections; o != NULL; o = o->next)
04603     {
04604       for (p = o->map_head.link_order;
04605           p != NULL;
04606           p = p->next)
04607        {
04608          if (p->type == bfd_indirect_link_order
04609              && (bfd_get_flavour (p->u.indirect.section->owner)
04610                 == bfd_target_ecoff_flavour))
04611            {
04612              if (! ecoff_indirect_link_order (abfd, info, o, p))
04613               return FALSE;
04614            }
04615          else if (p->type == bfd_section_reloc_link_order
04616                  || p->type == bfd_symbol_reloc_link_order)
04617            {
04618              if (! ecoff_reloc_link_order (abfd, info, o, p))
04619               return FALSE;
04620            }
04621          else
04622            {
04623              if (! _bfd_default_link_order (abfd, info, o, p))
04624               return FALSE;
04625            }
04626        }
04627     }
04628 
04629   bfd_get_symcount (abfd) = symhdr->iextMax + symhdr->isymMax;
04630 
04631   ecoff_data (abfd)->linker = TRUE;
04632 
04633   return TRUE;
04634 }