[BACK]Return to ecofflink.c CVS log [TXT][DIR] Up to [cvs.NetBSD.org] / src / external / gpl3 / binutils.old / dist / bfd

Annotation of src/external/gpl3/binutils.old/dist/bfd/ecofflink.c, Revision 1.1.1.3

1.1       christos    1: /* Routines to link ECOFF debugging information.
1.1.1.3 ! christos    2:    Copyright (C) 1993-2016 Free Software Foundation, Inc.
1.1       christos    3:    Written by Ian Lance Taylor, Cygnus Support, <ian@cygnus.com>.
                      4:
                      5:    This file is part of BFD, the Binary File Descriptor library.
                      6:
                      7:    This program is free software; you can redistribute it and/or modify
                      8:    it under the terms of the GNU General Public License as published by
                      9:    the Free Software Foundation; either version 3 of the License, or
                     10:    (at your option) any later version.
                     11:
                     12:    This program is distributed in the hope that it will be useful,
                     13:    but WITHOUT ANY WARRANTY; without even the implied warranty of
                     14:    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
                     15:    GNU General Public License for more details.
                     16:
                     17:    You should have received a copy of the GNU General Public License
                     18:    along with this program; if not, write to the Free Software
                     19:    Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
                     20:    MA 02110-1301, USA.  */
                     21:
                     22: #include "sysdep.h"
                     23: #include "bfd.h"
                     24: #include "bfdlink.h"
                     25: #include "libbfd.h"
                     26: #include "objalloc.h"
                     27: #include "aout/stab_gnu.h"
                     28: #include "coff/internal.h"
                     29: #include "coff/sym.h"
                     30: #include "coff/symconst.h"
                     31: #include "coff/ecoff.h"
                     32: #include "libcoff.h"
                     33: #include "libecoff.h"
                     34: 
                     35: /* Routines to swap auxiliary information in and out.  I am assuming
                     36:    that the auxiliary information format is always going to be target
                     37:    independent.  */
                     38:
                     39: /* Swap in a type information record.
                     40:    BIGEND says whether AUX symbols are big-endian or little-endian; this
                     41:    info comes from the file header record (fh-fBigendian).  */
                     42:
                     43: void
                     44: _bfd_ecoff_swap_tir_in (int bigend, const struct tir_ext *ext_copy,
                     45:                        TIR *intern)
                     46: {
                     47:   struct tir_ext ext[1];
                     48:
                     49:   *ext = *ext_copy;            /* Make it reasonable to do in-place.  */
                     50:
                     51:   /* now the fun stuff...  */
                     52:   if (bigend)
                     53:     {
                     54:       intern->fBitfield   = 0 != (ext->t_bits1[0] & TIR_BITS1_FBITFIELD_BIG);
                     55:       intern->continued   = 0 != (ext->t_bits1[0] & TIR_BITS1_CONTINUED_BIG);
                     56:       intern->bt          = (ext->t_bits1[0] & TIR_BITS1_BT_BIG)
                     57:                           >>                   TIR_BITS1_BT_SH_BIG;
                     58:       intern->tq4         = (ext->t_tq45[0] & TIR_BITS_TQ4_BIG)
                     59:                          >>                  TIR_BITS_TQ4_SH_BIG;
                     60:       intern->tq5         = (ext->t_tq45[0] & TIR_BITS_TQ5_BIG)
                     61:                          >>                  TIR_BITS_TQ5_SH_BIG;
                     62:       intern->tq0         = (ext->t_tq01[0] & TIR_BITS_TQ0_BIG)
                     63:                          >>                  TIR_BITS_TQ0_SH_BIG;
                     64:       intern->tq1         = (ext->t_tq01[0] & TIR_BITS_TQ1_BIG)
                     65:                          >>                  TIR_BITS_TQ1_SH_BIG;
                     66:       intern->tq2         = (ext->t_tq23[0] & TIR_BITS_TQ2_BIG)
                     67:                          >>                  TIR_BITS_TQ2_SH_BIG;
                     68:       intern->tq3         = (ext->t_tq23[0] & TIR_BITS_TQ3_BIG)
                     69:                          >>                  TIR_BITS_TQ3_SH_BIG;
                     70:     }
                     71:   else
                     72:     {
                     73:       intern->fBitfield   = 0 != (ext->t_bits1[0] & TIR_BITS1_FBITFIELD_LITTLE);
                     74:       intern->continued   = 0 != (ext->t_bits1[0] & TIR_BITS1_CONTINUED_LITTLE);
                     75:       intern->bt          = (ext->t_bits1[0] & TIR_BITS1_BT_LITTLE)
                     76:                          >>                TIR_BITS1_BT_SH_LITTLE;
                     77:       intern->tq4         = (ext->t_tq45[0] & TIR_BITS_TQ4_LITTLE)
                     78:                          >>                TIR_BITS_TQ4_SH_LITTLE;
                     79:       intern->tq5         = (ext->t_tq45[0] & TIR_BITS_TQ5_LITTLE)
                     80:                          >>                TIR_BITS_TQ5_SH_LITTLE;
                     81:       intern->tq0         = (ext->t_tq01[0] & TIR_BITS_TQ0_LITTLE)
                     82:                          >>                TIR_BITS_TQ0_SH_LITTLE;
                     83:       intern->tq1         = (ext->t_tq01[0] & TIR_BITS_TQ1_LITTLE)
                     84:                          >>                TIR_BITS_TQ1_SH_LITTLE;
                     85:       intern->tq2         = (ext->t_tq23[0] & TIR_BITS_TQ2_LITTLE)
                     86:                          >>                TIR_BITS_TQ2_SH_LITTLE;
                     87:       intern->tq3         = (ext->t_tq23[0] & TIR_BITS_TQ3_LITTLE)
                     88:                          >>                TIR_BITS_TQ3_SH_LITTLE;
                     89:     }
                     90:
                     91: #ifdef TEST
                     92:   if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
                     93:     abort ();
                     94: #endif
                     95: }
                     96:
                     97: /* Swap out a type information record.
                     98:    BIGEND says whether AUX symbols are big-endian or little-endian; this
                     99:    info comes from the file header record (fh-fBigendian).  */
                    100:
                    101: void
                    102: _bfd_ecoff_swap_tir_out (int bigend,
                    103:                         const TIR *intern_copy,
                    104:                         struct tir_ext *ext)
                    105: {
                    106:   TIR intern[1];
                    107:
                    108:   *intern = *intern_copy;      /* Make it reasonable to do in-place.  */
                    109:
                    110:   /* now the fun stuff...  */
                    111:   if (bigend)
                    112:     {
                    113:       ext->t_bits1[0] = ((intern->fBitfield ? TIR_BITS1_FBITFIELD_BIG : 0)
                    114:                       | (intern->continued ? TIR_BITS1_CONTINUED_BIG : 0)
                    115:                       | ((intern->bt << TIR_BITS1_BT_SH_BIG)
                    116:                          & TIR_BITS1_BT_BIG));
                    117:       ext->t_tq45[0] = (((intern->tq4 << TIR_BITS_TQ4_SH_BIG)
                    118:                       & TIR_BITS_TQ4_BIG)
                    119:                      | ((intern->tq5 << TIR_BITS_TQ5_SH_BIG)
                    120:                         & TIR_BITS_TQ5_BIG));
                    121:       ext->t_tq01[0] = (((intern->tq0 << TIR_BITS_TQ0_SH_BIG)
                    122:                       & TIR_BITS_TQ0_BIG)
                    123:                      | ((intern->tq1 << TIR_BITS_TQ1_SH_BIG)
                    124:                         & TIR_BITS_TQ1_BIG));
                    125:       ext->t_tq23[0] = (((intern->tq2 << TIR_BITS_TQ2_SH_BIG)
                    126:                       & TIR_BITS_TQ2_BIG)
                    127:                      | ((intern->tq3 << TIR_BITS_TQ3_SH_BIG)
                    128:                         & TIR_BITS_TQ3_BIG));
                    129:     }
                    130:   else
                    131:     {
                    132:       ext->t_bits1[0] = ((intern->fBitfield ? TIR_BITS1_FBITFIELD_LITTLE : 0)
                    133:                       | (intern->continued ? TIR_BITS1_CONTINUED_LITTLE : 0)
                    134:                       | ((intern->bt << TIR_BITS1_BT_SH_LITTLE)
                    135:                          & TIR_BITS1_BT_LITTLE));
                    136:       ext->t_tq45[0] = (((intern->tq4 << TIR_BITS_TQ4_SH_LITTLE)
                    137:                       & TIR_BITS_TQ4_LITTLE)
                    138:                      | ((intern->tq5 << TIR_BITS_TQ5_SH_LITTLE)
                    139:                         & TIR_BITS_TQ5_LITTLE));
                    140:       ext->t_tq01[0] = (((intern->tq0 << TIR_BITS_TQ0_SH_LITTLE)
                    141:                       & TIR_BITS_TQ0_LITTLE)
                    142:                      | ((intern->tq1 << TIR_BITS_TQ1_SH_LITTLE)
                    143:                         & TIR_BITS_TQ1_LITTLE));
                    144:       ext->t_tq23[0] = (((intern->tq2 << TIR_BITS_TQ2_SH_LITTLE)
                    145:                       & TIR_BITS_TQ2_LITTLE)
                    146:                      | ((intern->tq3 << TIR_BITS_TQ3_SH_LITTLE)
                    147:                         & TIR_BITS_TQ3_LITTLE));
                    148:     }
                    149:
                    150: #ifdef TEST
                    151:   if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
                    152:     abort ();
                    153: #endif
                    154: }
                    155:
                    156: /* Swap in a relative symbol record.  BIGEND says whether it is in
                    157:    big-endian or little-endian format.*/
                    158:
                    159: void
                    160: _bfd_ecoff_swap_rndx_in (int bigend,
                    161:                         const struct rndx_ext *ext_copy,
                    162:                         RNDXR *intern)
                    163: {
                    164:   struct rndx_ext ext[1];
                    165:
                    166:   *ext = *ext_copy;            /* Make it reasonable to do in-place.  */
                    167:
                    168:   /* now the fun stuff...  */
                    169:   if (bigend)
                    170:     {
                    171:       intern->rfd   = (ext->r_bits[0] << RNDX_BITS0_RFD_SH_LEFT_BIG)
                    172:                  | ((ext->r_bits[1] & RNDX_BITS1_RFD_BIG)
                    173:                                    >> RNDX_BITS1_RFD_SH_BIG);
                    174:       intern->index = ((ext->r_bits[1] & RNDX_BITS1_INDEX_BIG)
                    175:                                    << RNDX_BITS1_INDEX_SH_LEFT_BIG)
                    176:                  | (ext->r_bits[2] << RNDX_BITS2_INDEX_SH_LEFT_BIG)
                    177:                  | (ext->r_bits[3] << RNDX_BITS3_INDEX_SH_LEFT_BIG);
                    178:     }
                    179:   else
                    180:     {
                    181:       intern->rfd   = (ext->r_bits[0] << RNDX_BITS0_RFD_SH_LEFT_LITTLE)
                    182:                  | ((ext->r_bits[1] & RNDX_BITS1_RFD_LITTLE)
                    183:                                    << RNDX_BITS1_RFD_SH_LEFT_LITTLE);
                    184:       intern->index = ((ext->r_bits[1] & RNDX_BITS1_INDEX_LITTLE)
                    185:                                    >> RNDX_BITS1_INDEX_SH_LITTLE)
                    186:                  | (ext->r_bits[2] << RNDX_BITS2_INDEX_SH_LEFT_LITTLE)
                    187:                  | ((unsigned int) ext->r_bits[3]
                    188:                     << RNDX_BITS3_INDEX_SH_LEFT_LITTLE);
                    189:     }
                    190:
                    191: #ifdef TEST
                    192:   if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
                    193:     abort ();
                    194: #endif
                    195: }
                    196:
                    197: /* Swap out a relative symbol record.  BIGEND says whether it is in
                    198:    big-endian or little-endian format.*/
                    199:
                    200: void
                    201: _bfd_ecoff_swap_rndx_out (int bigend,
                    202:                          const RNDXR *intern_copy,
                    203:                          struct rndx_ext *ext)
                    204: {
                    205:   RNDXR intern[1];
                    206:
                    207:   *intern = *intern_copy;      /* Make it reasonable to do in-place.  */
                    208:
                    209:   /* now the fun stuff...  */
                    210:   if (bigend)
                    211:     {
                    212:       ext->r_bits[0] = intern->rfd >> RNDX_BITS0_RFD_SH_LEFT_BIG;
                    213:       ext->r_bits[1] = (((intern->rfd << RNDX_BITS1_RFD_SH_BIG)
                    214:                       & RNDX_BITS1_RFD_BIG)
                    215:                      | ((intern->index >> RNDX_BITS1_INDEX_SH_LEFT_BIG)
                    216:                         & RNDX_BITS1_INDEX_BIG));
                    217:       ext->r_bits[2] = intern->index >> RNDX_BITS2_INDEX_SH_LEFT_BIG;
                    218:       ext->r_bits[3] = intern->index >> RNDX_BITS3_INDEX_SH_LEFT_BIG;
                    219:     }
                    220:   else
                    221:     {
                    222:       ext->r_bits[0] = intern->rfd >> RNDX_BITS0_RFD_SH_LEFT_LITTLE;
                    223:       ext->r_bits[1] = (((intern->rfd >> RNDX_BITS1_RFD_SH_LEFT_LITTLE)
                    224:                       & RNDX_BITS1_RFD_LITTLE)
                    225:                      | ((intern->index << RNDX_BITS1_INDEX_SH_LITTLE)
                    226:                         & RNDX_BITS1_INDEX_LITTLE));
                    227:       ext->r_bits[2] = intern->index >> RNDX_BITS2_INDEX_SH_LEFT_LITTLE;
                    228:       ext->r_bits[3] = intern->index >> RNDX_BITS3_INDEX_SH_LEFT_LITTLE;
                    229:     }
                    230:
                    231: #ifdef TEST
                    232:   if (memcmp ((char *)ext, (char *)intern, sizeof (*intern)) != 0)
                    233:     abort ();
                    234: #endif
                    235: }
                    236: 
                    237: /* The minimum amount of data to allocate.  */
                    238: #define ALLOC_SIZE (4064)
                    239:
                    240: /* Add bytes to a buffer.  Return success.  */
                    241:
                    242: static bfd_boolean
                    243: ecoff_add_bytes (char **buf, char **bufend, size_t need)
                    244: {
                    245:   size_t have;
                    246:   size_t want;
                    247:   char *newbuf;
                    248:
                    249:   have = *bufend - *buf;
                    250:   if (have > need)
                    251:     want = ALLOC_SIZE;
                    252:   else
                    253:     {
                    254:       want = need - have;
                    255:       if (want < ALLOC_SIZE)
                    256:        want = ALLOC_SIZE;
                    257:     }
                    258:   newbuf = (char *) bfd_realloc (*buf, (bfd_size_type) have + want);
                    259:   if (newbuf == NULL)
                    260:     return FALSE;
                    261:   *buf = newbuf;
                    262:   *bufend = *buf + have + want;
                    263:   return TRUE;
                    264: }
                    265:
                    266: /* We keep a hash table which maps strings to numbers.  We use it to
                    267:    map FDR names to indices in the output file, and to map local
                    268:    strings when combining stabs debugging information.  */
                    269:
                    270: struct string_hash_entry
                    271: {
                    272:   struct bfd_hash_entry root;
                    273:   /* FDR index or string table offset.  */
                    274:   long val;
                    275:   /* Next entry in string table.  */
                    276:   struct string_hash_entry *next;
                    277: };
                    278:
                    279: struct string_hash_table
                    280: {
                    281:   struct bfd_hash_table table;
                    282: };
                    283:
                    284: /* Routine to create an entry in a string hash table.  */
                    285:
                    286: static struct bfd_hash_entry *
                    287: string_hash_newfunc (struct bfd_hash_entry *entry,
                    288:                     struct bfd_hash_table *table,
                    289:                     const char *string)
                    290: {
                    291:   struct string_hash_entry *ret = (struct string_hash_entry *) entry;
                    292:
                    293:   /* Allocate the structure if it has not already been allocated by a
                    294:      subclass.  */
                    295:   if (ret == (struct string_hash_entry *) NULL)
                    296:     ret = ((struct string_hash_entry *)
                    297:           bfd_hash_allocate (table, sizeof (struct string_hash_entry)));
                    298:   if (ret == (struct string_hash_entry *) NULL)
                    299:     return NULL;
                    300:
                    301:   /* Call the allocation method of the superclass.  */
                    302:   ret = ((struct string_hash_entry *)
                    303:         bfd_hash_newfunc ((struct bfd_hash_entry *) ret, table, string));
                    304:
                    305:   if (ret)
                    306:     {
                    307:       /* Initialize the local fields.  */
                    308:       ret->val = -1;
                    309:       ret->next = NULL;
                    310:     }
                    311:
                    312:   return (struct bfd_hash_entry *) ret;
                    313: }
                    314:
                    315: /* Look up an entry in an string hash table.  */
                    316:
                    317: #define string_hash_lookup(t, string, create, copy) \
                    318:   ((struct string_hash_entry *) \
                    319:    bfd_hash_lookup (&(t)->table, (string), (create), (copy)))
                    320:
                    321: /* We can't afford to read in all the debugging information when we do
                    322:    a link.  Instead, we build a list of these structures to show how
                    323:    different parts of the input file map to the output file.  */
                    324:
                    325: struct shuffle
                    326: {
                    327:   /* The next entry in this linked list.  */
                    328:   struct shuffle *next;
                    329:   /* The length of the information.  */
                    330:   unsigned long size;
                    331:   /* Whether this information comes from a file or not.  */
                    332:   bfd_boolean filep;
                    333:   union
                    334:     {
                    335:       struct
                    336:        {
                    337:          /* The BFD the data comes from.  */
                    338:          bfd *input_bfd;
                    339:          /* The offset within input_bfd.  */
                    340:          file_ptr offset;
                    341:        } file;
                    342:       /* The data to be written out.  */
                    343:       void * memory;
                    344:     } u;
                    345: };
                    346:
                    347: /* This structure holds information across calls to
                    348:    bfd_ecoff_debug_accumulate.  */
                    349:
                    350: struct accumulate
                    351: {
                    352:   /* The FDR hash table.  */
                    353:   struct string_hash_table fdr_hash;
                    354:   /* The strings hash table.  */
                    355:   struct string_hash_table str_hash;
                    356:   /* Linked lists describing how to shuffle the input debug
                    357:      information into the output file.  We keep a pointer to both the
                    358:      head and the tail.  */
                    359:   struct shuffle *line;
                    360:   struct shuffle *line_end;
                    361:   struct shuffle *pdr;
                    362:   struct shuffle *pdr_end;
                    363:   struct shuffle *sym;
                    364:   struct shuffle *sym_end;
                    365:   struct shuffle *opt;
                    366:   struct shuffle *opt_end;
                    367:   struct shuffle *aux;
                    368:   struct shuffle *aux_end;
                    369:   struct shuffle *ss;
                    370:   struct shuffle *ss_end;
                    371:   struct string_hash_entry *ss_hash;
                    372:   struct string_hash_entry *ss_hash_end;
                    373:   struct shuffle *fdr;
                    374:   struct shuffle *fdr_end;
                    375:   struct shuffle *rfd;
                    376:   struct shuffle *rfd_end;
                    377:   /* The size of the largest file shuffle.  */
                    378:   unsigned long largest_file_shuffle;
                    379:   /* An objalloc for debugging information.  */
                    380:   struct objalloc *memory;
                    381: };
                    382:
                    383: /* Add a file entry to a shuffle list.  */
                    384:
                    385: static bfd_boolean
                    386: add_file_shuffle (struct accumulate *ainfo,
                    387:                  struct shuffle **head,
                    388:                  struct shuffle **tail,
                    389:                  bfd *input_bfd,
                    390:                  file_ptr offset,
                    391:                  unsigned long size)
                    392: {
                    393:   struct shuffle *n;
                    394:
                    395:   if (*tail != (struct shuffle *) NULL
                    396:       && (*tail)->filep
                    397:       && (*tail)->u.file.input_bfd == input_bfd
                    398:       && (*tail)->u.file.offset + (*tail)->size == (unsigned long) offset)
                    399:     {
                    400:       /* Just merge this entry onto the existing one.  */
                    401:       (*tail)->size += size;
                    402:       if ((*tail)->size > ainfo->largest_file_shuffle)
                    403:        ainfo->largest_file_shuffle = (*tail)->size;
                    404:       return TRUE;
                    405:     }
                    406:
                    407:   n = (struct shuffle *) objalloc_alloc (ainfo->memory,
                    408:                                         sizeof (struct shuffle));
                    409:   if (!n)
                    410:     {
                    411:       bfd_set_error (bfd_error_no_memory);
                    412:       return FALSE;
                    413:     }
                    414:   n->next = NULL;
                    415:   n->size = size;
                    416:   n->filep = TRUE;
                    417:   n->u.file.input_bfd = input_bfd;
                    418:   n->u.file.offset = offset;
                    419:   if (*head == (struct shuffle *) NULL)
                    420:     *head = n;
                    421:   if (*tail != (struct shuffle *) NULL)
                    422:     (*tail)->next = n;
                    423:   *tail = n;
                    424:   if (size > ainfo->largest_file_shuffle)
                    425:     ainfo->largest_file_shuffle = size;
                    426:   return TRUE;
                    427: }
                    428:
                    429: /* Add a memory entry to a shuffle list.  */
                    430:
                    431: static bfd_boolean
                    432: add_memory_shuffle (struct accumulate *ainfo,
                    433:                    struct shuffle **head,
                    434:                    struct shuffle **tail,
                    435:                    bfd_byte *data,
                    436:                    unsigned long size)
                    437: {
                    438:   struct shuffle *n;
                    439:
                    440:   n = (struct shuffle *) objalloc_alloc (ainfo->memory,
                    441:                                         sizeof (struct shuffle));
                    442:   if (!n)
                    443:     {
                    444:       bfd_set_error (bfd_error_no_memory);
                    445:       return FALSE;
                    446:     }
                    447:   n->next = NULL;
                    448:   n->size = size;
                    449:   n->filep = FALSE;
                    450:   n->u.memory = data;
                    451:   if (*head == (struct shuffle *) NULL)
                    452:     *head = n;
                    453:   if (*tail != (struct shuffle *) NULL)
                    454:     (*tail)->next = n;
                    455:   *tail = n;
                    456:   return TRUE;
                    457: }
                    458:
                    459: /* Initialize the FDR hash table.  This returns a handle which is then
                    460:    passed in to bfd_ecoff_debug_accumulate, et. al.  */
                    461:
                    462: void *
                    463: bfd_ecoff_debug_init (bfd *output_bfd ATTRIBUTE_UNUSED,
                    464:                      struct ecoff_debug_info *output_debug,
                    465:                      const struct ecoff_debug_swap *output_swap ATTRIBUTE_UNUSED,
                    466:                      struct bfd_link_info *info)
                    467: {
                    468:   struct accumulate *ainfo;
                    469:   bfd_size_type amt = sizeof (struct accumulate);
                    470:
                    471:   ainfo = (struct accumulate *) bfd_malloc (amt);
                    472:   if (!ainfo)
                    473:     return NULL;
                    474:   if (!bfd_hash_table_init_n (&ainfo->fdr_hash.table, string_hash_newfunc,
                    475:                              sizeof (struct string_hash_entry), 1021))
                    476:     return NULL;
                    477:
                    478:   ainfo->line = NULL;
                    479:   ainfo->line_end = NULL;
                    480:   ainfo->pdr = NULL;
                    481:   ainfo->pdr_end = NULL;
                    482:   ainfo->sym = NULL;
                    483:   ainfo->sym_end = NULL;
                    484:   ainfo->opt = NULL;
                    485:   ainfo->opt_end = NULL;
                    486:   ainfo->aux = NULL;
                    487:   ainfo->aux_end = NULL;
                    488:   ainfo->ss = NULL;
                    489:   ainfo->ss_end = NULL;
                    490:   ainfo->ss_hash = NULL;
                    491:   ainfo->ss_hash_end = NULL;
                    492:   ainfo->fdr = NULL;
                    493:   ainfo->fdr_end = NULL;
                    494:   ainfo->rfd = NULL;
                    495:   ainfo->rfd_end = NULL;
                    496:
                    497:   ainfo->largest_file_shuffle = 0;
                    498:
1.1.1.2   christos  499:   if (! bfd_link_relocatable (info))
1.1       christos  500:     {
                    501:       if (!bfd_hash_table_init (&ainfo->str_hash.table, string_hash_newfunc,
                    502:                                sizeof (struct string_hash_entry)))
                    503:        return NULL;
                    504:
                    505:       /* The first entry in the string table is the empty string.  */
                    506:       output_debug->symbolic_header.issMax = 1;
                    507:     }
                    508:
                    509:   ainfo->memory = objalloc_create ();
                    510:   if (ainfo->memory == NULL)
                    511:     {
                    512:       bfd_set_error (bfd_error_no_memory);
                    513:       return NULL;
                    514:     }
                    515:
                    516:   return ainfo;
                    517: }
                    518:
                    519: /* Free the accumulated debugging information.  */
                    520:
                    521: void
                    522: bfd_ecoff_debug_free (void * handle,
                    523:                      bfd *output_bfd ATTRIBUTE_UNUSED,
                    524:                      struct ecoff_debug_info *output_debug ATTRIBUTE_UNUSED,
                    525:                      const struct ecoff_debug_swap *output_swap ATTRIBUTE_UNUSED,
                    526:                      struct bfd_link_info *info)
                    527: {
                    528:   struct accumulate *ainfo = (struct accumulate *) handle;
                    529:
                    530:   bfd_hash_table_free (&ainfo->fdr_hash.table);
                    531:
1.1.1.2   christos  532:   if (! bfd_link_relocatable (info))
1.1       christos  533:     bfd_hash_table_free (&ainfo->str_hash.table);
                    534:
                    535:   objalloc_free (ainfo->memory);
                    536:
                    537:   free (ainfo);
                    538: }
                    539:
                    540: /* Accumulate the debugging information from INPUT_BFD into
                    541:    OUTPUT_BFD.  The INPUT_DEBUG argument points to some ECOFF
                    542:    debugging information which we want to link into the information
                    543:    pointed to by the OUTPUT_DEBUG argument.  OUTPUT_SWAP and
                    544:    INPUT_SWAP point to the swapping information needed.  INFO is the
                    545:    linker information structure.  HANDLE is returned by
                    546:    bfd_ecoff_debug_init.  */
                    547:
                    548: bfd_boolean
                    549: bfd_ecoff_debug_accumulate (void * handle,
                    550:                            bfd *output_bfd,
                    551:                            struct ecoff_debug_info *output_debug,
                    552:                            const struct ecoff_debug_swap *output_swap,
                    553:                            bfd *input_bfd,
                    554:                            struct ecoff_debug_info *input_debug,
                    555:                            const struct ecoff_debug_swap *input_swap,
                    556:                            struct bfd_link_info *info)
                    557: {
                    558:   struct accumulate *ainfo = (struct accumulate *) handle;
                    559:   void (* const swap_sym_in) (bfd *, void *, SYMR *)
                    560:     = input_swap->swap_sym_in;
                    561:   void (* const swap_rfd_in) (bfd *, void *, RFDT *)
                    562:     = input_swap->swap_rfd_in;
                    563:   void (* const swap_sym_out) (bfd *, const SYMR *, void *)
                    564:     = output_swap->swap_sym_out;
                    565:   void (* const swap_fdr_out) (bfd *, const FDR *, void *)
                    566:     = output_swap->swap_fdr_out;
                    567:   void (* const swap_rfd_out) (bfd *, const RFDT *, void *)
                    568:     = output_swap->swap_rfd_out;
                    569:   bfd_size_type external_pdr_size = output_swap->external_pdr_size;
                    570:   bfd_size_type external_sym_size = output_swap->external_sym_size;
                    571:   bfd_size_type external_opt_size = output_swap->external_opt_size;
                    572:   bfd_size_type external_fdr_size = output_swap->external_fdr_size;
                    573:   bfd_size_type external_rfd_size = output_swap->external_rfd_size;
                    574:   HDRR * const output_symhdr = &output_debug->symbolic_header;
                    575:   HDRR * const input_symhdr = &input_debug->symbolic_header;
                    576:   bfd_vma section_adjust[scMax];
                    577:   asection *sec;
                    578:   bfd_byte *fdr_start;
                    579:   bfd_byte *fdr_ptr;
                    580:   bfd_byte *fdr_end;
                    581:   bfd_size_type fdr_add;
                    582:   unsigned int copied;
                    583:   RFDT i;
                    584:   unsigned long sz;
                    585:   bfd_byte *rfd_out;
                    586:   bfd_byte *rfd_in;
                    587:   bfd_byte *rfd_end;
                    588:   long newrfdbase = 0;
                    589:   long oldrfdbase = 0;
                    590:   bfd_byte *fdr_out;
                    591:   bfd_size_type amt;
                    592:
                    593:   /* Use section_adjust to hold the value to add to a symbol in a
                    594:      particular section.  */
                    595:   memset (section_adjust, 0, sizeof section_adjust);
                    596:
                    597: #define SET(name, indx) \
                    598:   sec = bfd_get_section_by_name (input_bfd, name); \
                    599:   if (sec != NULL) \
                    600:     section_adjust[indx] = (sec->output_section->vma \
                    601:                            + sec->output_offset \
                    602:                            - sec->vma);
                    603:
                    604:   SET (".text", scText);
                    605:   SET (".data", scData);
                    606:   SET (".bss", scBss);
                    607:   SET (".sdata", scSData);
                    608:   SET (".sbss", scSBss);
                    609:   /* scRdata section may be either .rdata or .rodata.  */
                    610:   SET (".rdata", scRData);
                    611:   SET (".rodata", scRData);
                    612:   SET (".init", scInit);
                    613:   SET (".fini", scFini);
                    614:   SET (".rconst", scRConst);
                    615:
                    616: #undef SET
                    617:
                    618:   /* Find all the debugging information based on the FDR's.  We need
                    619:      to handle them whether they are swapped or not.  */
                    620:   if (input_debug->fdr != (FDR *) NULL)
                    621:     {
                    622:       fdr_start = (bfd_byte *) input_debug->fdr;
                    623:       fdr_add = sizeof (FDR);
                    624:     }
                    625:   else
                    626:     {
                    627:       fdr_start = (bfd_byte *) input_debug->external_fdr;
                    628:       fdr_add = input_swap->external_fdr_size;
                    629:     }
                    630:   fdr_end = fdr_start + input_symhdr->ifdMax * fdr_add;
                    631:
                    632:   amt = input_symhdr->ifdMax;
                    633:   amt *= sizeof (RFDT);
                    634:   input_debug->ifdmap = (RFDT *) bfd_alloc (input_bfd, amt);
                    635:
                    636:   sz = (input_symhdr->crfd + input_symhdr->ifdMax) * external_rfd_size;
                    637:   rfd_out = (bfd_byte *) objalloc_alloc (ainfo->memory, sz);
                    638:   if (!input_debug->ifdmap || !rfd_out)
                    639:     {
                    640:       bfd_set_error (bfd_error_no_memory);
                    641:       return FALSE;
                    642:     }
                    643:   if (!add_memory_shuffle (ainfo, &ainfo->rfd, &ainfo->rfd_end, rfd_out, sz))
                    644:     return FALSE;
                    645:
                    646:   copied = 0;
                    647:
                    648:   /* Look through the FDR's to see which ones we are going to include
                    649:      in the final output.  We do not want duplicate FDR information
                    650:      for header files, because ECOFF debugging is often very large.
                    651:      When we find an FDR with no line information which can be merged,
                    652:      we look it up in a hash table to ensure that we only include it
                    653:      once.  We keep a table mapping FDR numbers to the final number
                    654:      they get with the BFD, so that we can refer to it when we write
                    655:      out the external symbols.  */
                    656:   for (fdr_ptr = fdr_start, i = 0;
                    657:        fdr_ptr < fdr_end;
                    658:        fdr_ptr += fdr_add, i++, rfd_out += external_rfd_size)
                    659:     {
                    660:       FDR fdr;
                    661:
                    662:       if (input_debug->fdr != (FDR *) NULL)
                    663:        fdr = *(FDR *) fdr_ptr;
                    664:       else
                    665:        (*input_swap->swap_fdr_in) (input_bfd, fdr_ptr, &fdr);
                    666:
                    667:       /* See if this FDR can be merged with an existing one.  */
                    668:       if (fdr.cbLine == 0 && fdr.rss != -1 && fdr.fMerge)
                    669:        {
                    670:          const char *name;
                    671:          char *lookup;
                    672:          struct string_hash_entry *fh;
                    673:
                    674:          /* We look up a string formed from the file name and the
                    675:             number of symbols and aux entries.  Sometimes an include
                    676:             file will conditionally define a typedef or something
                    677:             based on the order of include files.  Using the number of
                    678:             symbols and aux entries as a hash reduces the chance that
                    679:             we will merge symbol information that should not be
                    680:             merged.  */
                    681:          name = input_debug->ss + fdr.issBase + fdr.rss;
                    682:
                    683:          lookup = (char *) bfd_malloc ((bfd_size_type) strlen (name) + 20);
                    684:          if (lookup == NULL)
                    685:            return FALSE;
                    686:          sprintf (lookup, "%s %lx %lx", name, (unsigned long) fdr.csym,
                    687:                   (unsigned long) fdr.caux);
                    688:
                    689:          fh = string_hash_lookup (&ainfo->fdr_hash, lookup, TRUE, TRUE);
                    690:          free (lookup);
                    691:          if (fh == (struct string_hash_entry *) NULL)
                    692:            return FALSE;
                    693:
                    694:          if (fh->val != -1)
                    695:            {
                    696:              input_debug->ifdmap[i] = fh->val;
                    697:              (*swap_rfd_out) (output_bfd, input_debug->ifdmap + i, rfd_out);
                    698:
                    699:              /* Don't copy this FDR.  */
                    700:              continue;
                    701:            }
                    702:
                    703:          fh->val = output_symhdr->ifdMax + copied;
                    704:        }
                    705:
                    706:       input_debug->ifdmap[i] = output_symhdr->ifdMax + copied;
                    707:       (*swap_rfd_out) (output_bfd, input_debug->ifdmap + i, rfd_out);
                    708:       ++copied;
                    709:     }
                    710:
                    711:   newrfdbase = output_symhdr->crfd;
                    712:   output_symhdr->crfd += input_symhdr->ifdMax;
                    713:
                    714:   /* Copy over any existing RFD's.  RFD's are only created by the
                    715:      linker, so this will only happen for input files which are the
                    716:      result of a partial link.  */
                    717:   rfd_in = (bfd_byte *) input_debug->external_rfd;
                    718:   rfd_end = rfd_in + input_symhdr->crfd * input_swap->external_rfd_size;
                    719:   for (;
                    720:        rfd_in < rfd_end;
                    721:        rfd_in += input_swap->external_rfd_size)
                    722:     {
                    723:       RFDT rfd;
                    724:
                    725:       (*swap_rfd_in) (input_bfd, rfd_in, &rfd);
                    726:       BFD_ASSERT (rfd >= 0 && rfd < input_symhdr->ifdMax);
                    727:       rfd = input_debug->ifdmap[rfd];
                    728:       (*swap_rfd_out) (output_bfd, &rfd, rfd_out);
                    729:       rfd_out += external_rfd_size;
                    730:     }
                    731:
                    732:   oldrfdbase = output_symhdr->crfd;
                    733:   output_symhdr->crfd += input_symhdr->crfd;
                    734:
                    735:   /* Look through the FDR's and copy over all associated debugging
                    736:      information.  */
                    737:   sz = copied * external_fdr_size;
                    738:   fdr_out = (bfd_byte *) objalloc_alloc (ainfo->memory, sz);
                    739:   if (!fdr_out)
                    740:     {
                    741:       bfd_set_error (bfd_error_no_memory);
                    742:       return FALSE;
                    743:     }
                    744:   if (!add_memory_shuffle (ainfo, &ainfo->fdr, &ainfo->fdr_end, fdr_out, sz))
                    745:     return FALSE;
                    746:   for (fdr_ptr = fdr_start, i = 0;
                    747:        fdr_ptr < fdr_end;
                    748:        fdr_ptr += fdr_add, i++)
                    749:     {
                    750:       FDR fdr;
                    751:       bfd_byte *sym_out;
                    752:       bfd_byte *lraw_src;
                    753:       bfd_byte *lraw_end;
                    754:       bfd_boolean fgotfilename;
                    755:
                    756:       if (input_debug->ifdmap[i] < output_symhdr->ifdMax)
                    757:        {
                    758:          /* We are not copying this FDR.  */
                    759:          continue;
                    760:        }
                    761:
                    762:       if (input_debug->fdr != (FDR *) NULL)
                    763:        fdr = *(FDR *) fdr_ptr;
                    764:       else
                    765:        (*input_swap->swap_fdr_in) (input_bfd, fdr_ptr, &fdr);
                    766:
                    767:       /* FIXME: It is conceivable that this FDR points to the .init or
                    768:         .fini section, in which case this will not do the right
                    769:         thing.  */
                    770:       fdr.adr += section_adjust[scText];
                    771:
                    772:       /* Swap in the local symbols, adjust their values, and swap them
                    773:         out again.  */
                    774:       fgotfilename = FALSE;
                    775:       sz = fdr.csym * external_sym_size;
                    776:       sym_out = (bfd_byte *) objalloc_alloc (ainfo->memory, sz);
                    777:       if (!sym_out)
                    778:        {
                    779:          bfd_set_error (bfd_error_no_memory);
                    780:          return FALSE;
                    781:        }
                    782:       if (!add_memory_shuffle (ainfo, &ainfo->sym, &ainfo->sym_end, sym_out,
                    783:                               sz))
                    784:        return FALSE;
                    785:       lraw_src = ((bfd_byte *) input_debug->external_sym
                    786:                  + fdr.isymBase * input_swap->external_sym_size);
                    787:       lraw_end = lraw_src + fdr.csym * input_swap->external_sym_size;
                    788:       for (;  lraw_src < lraw_end;  lraw_src += input_swap->external_sym_size)
                    789:        {
                    790:          SYMR internal_sym;
                    791:
                    792:          (*swap_sym_in) (input_bfd, lraw_src, &internal_sym);
                    793:
                    794:          BFD_ASSERT (internal_sym.sc != scCommon
                    795:                      && internal_sym.sc != scSCommon);
                    796:
                    797:          /* Adjust the symbol value if appropriate.  */
                    798:          switch (internal_sym.st)
                    799:            {
                    800:            case stNil:
                    801:              if (ECOFF_IS_STAB (&internal_sym))
                    802:                break;
                    803:              /* Fall through.  */
                    804:            case stGlobal:
                    805:            case stStatic:
                    806:            case stLabel:
                    807:            case stProc:
                    808:            case stStaticProc:
                    809:              internal_sym.value += section_adjust[internal_sym.sc];
                    810:              break;
                    811:
                    812:            default:
                    813:              break;
                    814:            }
                    815:
                    816:          /* If we are doing a final link, we hash all the strings in
                    817:             the local symbol table together.  This reduces the amount
                    818:             of space required by debugging information.  We don't do
                    819:             this when performing a relocatable link because it would
                    820:             prevent us from easily merging different FDR's.  */
1.1.1.2   christos  821:          if (! bfd_link_relocatable (info))
1.1       christos  822:            {
                    823:              bfd_boolean ffilename;
                    824:              const char *name;
                    825:
                    826:              if (! fgotfilename && internal_sym.iss == fdr.rss)
                    827:                ffilename = TRUE;
                    828:              else
                    829:                ffilename = FALSE;
                    830:
                    831:              /* Hash the name into the string table.  */
                    832:              name = input_debug->ss + fdr.issBase + internal_sym.iss;
                    833:              if (*name == '\0')
                    834:                internal_sym.iss = 0;
                    835:              else
                    836:                {
                    837:                  struct string_hash_entry *sh;
                    838:
                    839:                  sh = string_hash_lookup (&ainfo->str_hash, name, TRUE, TRUE);
                    840:                  if (sh == (struct string_hash_entry *) NULL)
                    841:                    return FALSE;
                    842:                  if (sh->val == -1)
                    843:                    {
                    844:                      sh->val = output_symhdr->issMax;
                    845:                      output_symhdr->issMax += strlen (name) + 1;
                    846:                      if (ainfo->ss_hash == (struct string_hash_entry *) NULL)
                    847:                        ainfo->ss_hash = sh;
                    848:                      if (ainfo->ss_hash_end
                    849:                          != (struct string_hash_entry *) NULL)
                    850:                        ainfo->ss_hash_end->next = sh;
                    851:                      ainfo->ss_hash_end = sh;
                    852:                    }
                    853:                  internal_sym.iss = sh->val;
                    854:                }
                    855:
                    856:              if (ffilename)
                    857:                {
                    858:                  fdr.rss = internal_sym.iss;
                    859:                  fgotfilename = TRUE;
                    860:                }
                    861:            }
                    862:
                    863:          (*swap_sym_out) (output_bfd, &internal_sym, sym_out);
                    864:          sym_out += external_sym_size;
                    865:        }
                    866:
                    867:       fdr.isymBase = output_symhdr->isymMax;
                    868:       output_symhdr->isymMax += fdr.csym;
                    869:
                    870:       /* Copy the information that does not need swapping.  */
                    871:
                    872:       /* FIXME: If we are relaxing, we need to adjust the line
                    873:         numbers.  Frankly, forget it.  Anybody using stabs debugging
                    874:         information will not use this line number information, and
                    875:         stabs are adjusted correctly.  */
                    876:       if (fdr.cbLine > 0)
                    877:        {
                    878:          file_ptr pos = input_symhdr->cbLineOffset + fdr.cbLineOffset;
                    879:          if (!add_file_shuffle (ainfo, &ainfo->line, &ainfo->line_end,
                    880:                                 input_bfd, pos, (unsigned long) fdr.cbLine))
                    881:            return FALSE;
                    882:          fdr.ilineBase = output_symhdr->ilineMax;
                    883:          fdr.cbLineOffset = output_symhdr->cbLine;
                    884:          output_symhdr->ilineMax += fdr.cline;
                    885:          output_symhdr->cbLine += fdr.cbLine;
                    886:        }
                    887:       if (fdr.caux > 0)
                    888:        {
                    889:          file_ptr pos = (input_symhdr->cbAuxOffset
                    890:                          + fdr.iauxBase * sizeof (union aux_ext));
                    891:          if (!add_file_shuffle (ainfo, &ainfo->aux, &ainfo->aux_end,
                    892:                                 input_bfd, pos,
                    893:                                 fdr.caux * sizeof (union aux_ext)))
                    894:            return FALSE;
                    895:          fdr.iauxBase = output_symhdr->iauxMax;
                    896:          output_symhdr->iauxMax += fdr.caux;
                    897:        }
1.1.1.2   christos  898:       if (! bfd_link_relocatable (info))
1.1       christos  899:        {
                    900:
                    901:          /* When are are hashing strings, we lie about the number of
                    902:             strings attached to each FDR.  We need to set cbSs
                    903:             because some versions of dbx apparently use it to decide
                    904:             how much of the string table to read in.  */
                    905:          fdr.issBase = 0;
                    906:          fdr.cbSs = output_symhdr->issMax;
                    907:        }
                    908:       else if (fdr.cbSs > 0)
                    909:        {
                    910:          file_ptr pos = input_symhdr->cbSsOffset + fdr.issBase;
                    911:          if (!add_file_shuffle (ainfo, &ainfo->ss, &ainfo->ss_end,
                    912:                                 input_bfd, pos, (unsigned long) fdr.cbSs))
                    913:            return FALSE;
                    914:          fdr.issBase = output_symhdr->issMax;
                    915:          output_symhdr->issMax += fdr.cbSs;
                    916:        }
                    917:
                    918:       if (output_bfd->xvec->header_byteorder
                    919:          == input_bfd->xvec->header_byteorder)
                    920:        {
                    921:          /* The two BFD's have the same endianness, and we don't have
                    922:             to adjust the PDR addresses, so simply copying the
                    923:             information will suffice.  */
                    924:          BFD_ASSERT (external_pdr_size == input_swap->external_pdr_size);
                    925:          if (fdr.cpd > 0)
                    926:            {
                    927:              file_ptr pos = (input_symhdr->cbPdOffset
                    928:                              + fdr.ipdFirst * external_pdr_size);
                    929:              unsigned long size = fdr.cpd * external_pdr_size;
                    930:              if (!add_file_shuffle (ainfo, &ainfo->pdr, &ainfo->pdr_end,
                    931:                                     input_bfd, pos, size))
                    932:                return FALSE;
                    933:            }
                    934:          BFD_ASSERT (external_opt_size == input_swap->external_opt_size);
                    935:          if (fdr.copt > 0)
                    936:            {
                    937:              file_ptr pos = (input_symhdr->cbOptOffset
                    938:                              + fdr.ioptBase * external_opt_size);
                    939:              unsigned long size = fdr.copt * external_opt_size;
                    940:              if (!add_file_shuffle (ainfo, &ainfo->opt, &ainfo->opt_end,
                    941:                                     input_bfd, pos, size))
                    942:                return FALSE;
                    943:            }
                    944:        }
                    945:       else
                    946:        {
                    947:          bfd_size_type outsz, insz;
                    948:          bfd_byte *in;
                    949:          bfd_byte *end;
                    950:          bfd_byte *out;
                    951:
                    952:          /* The two BFD's have different endianness, so we must swap
                    953:             everything in and out.  This code would always work, but
                    954:             it would be unnecessarily slow in the normal case.  */
                    955:          outsz = external_pdr_size;
                    956:          insz = input_swap->external_pdr_size;
                    957:          in = ((bfd_byte *) input_debug->external_pdr
                    958:                + fdr.ipdFirst * insz);
                    959:          end = in + fdr.cpd * insz;
                    960:          sz = fdr.cpd * outsz;
                    961:          out = (bfd_byte *) objalloc_alloc (ainfo->memory, sz);
                    962:          if (!out)
                    963:            {
                    964:              bfd_set_error (bfd_error_no_memory);
                    965:              return FALSE;
                    966:            }
                    967:          if (!add_memory_shuffle (ainfo, &ainfo->pdr, &ainfo->pdr_end, out,
                    968:                                   sz))
                    969:            return FALSE;
                    970:          for (; in < end; in += insz, out += outsz)
                    971:            {
                    972:              PDR pdr;
                    973:
                    974:              (*input_swap->swap_pdr_in) (input_bfd, in, &pdr);
                    975:              (*output_swap->swap_pdr_out) (output_bfd, &pdr, out);
                    976:            }
                    977:
                    978:          /* Swap over the optimization information.  */
                    979:          outsz = external_opt_size;
                    980:          insz = input_swap->external_opt_size;
                    981:          in = ((bfd_byte *) input_debug->external_opt
                    982:                + fdr.ioptBase * insz);
                    983:          end = in + fdr.copt * insz;
                    984:          sz = fdr.copt * outsz;
                    985:          out = (bfd_byte *) objalloc_alloc (ainfo->memory, sz);
                    986:          if (!out)
                    987:            {
                    988:              bfd_set_error (bfd_error_no_memory);
                    989:              return FALSE;
                    990:            }
                    991:          if (!add_memory_shuffle (ainfo, &ainfo->opt, &ainfo->opt_end, out,
                    992:                                   sz))
                    993:            return FALSE;
                    994:          for (; in < end; in += insz, out += outsz)
                    995:            {
                    996:              OPTR opt;
                    997:
                    998:              (*input_swap->swap_opt_in) (input_bfd, in, &opt);
                    999:              (*output_swap->swap_opt_out) (output_bfd, &opt, out);
                   1000:            }
                   1001:        }
                   1002:
                   1003:       fdr.ipdFirst = output_symhdr->ipdMax;
                   1004:       output_symhdr->ipdMax += fdr.cpd;
                   1005:       fdr.ioptBase = output_symhdr->ioptMax;
                   1006:       output_symhdr->ioptMax += fdr.copt;
                   1007:
                   1008:       if (fdr.crfd <= 0)
                   1009:        {
                   1010:          /* Point this FDR at the table of RFD's we created.  */
                   1011:          fdr.rfdBase = newrfdbase;
                   1012:          fdr.crfd = input_symhdr->ifdMax;
                   1013:        }
                   1014:       else
                   1015:        {
                   1016:          /* Point this FDR at the remapped RFD's.  */
                   1017:          fdr.rfdBase += oldrfdbase;
                   1018:        }
                   1019:
                   1020:       (*swap_fdr_out) (output_bfd, &fdr, fdr_out);
                   1021:       fdr_out += external_fdr_size;
                   1022:       ++output_symhdr->ifdMax;
                   1023:     }
                   1024:
                   1025:   return TRUE;
                   1026: }
                   1027:
                   1028: /* Add a string to the debugging information we are accumulating.
                   1029:    Return the offset from the fdr string base.  */
                   1030:
                   1031: static long
                   1032: ecoff_add_string (struct accumulate *ainfo,
                   1033:                  struct bfd_link_info *info,
                   1034:                  struct ecoff_debug_info *debug,
                   1035:                  FDR *fdr,
                   1036:                  const char *string)
                   1037: {
                   1038:   HDRR *symhdr;
                   1039:   size_t len;
                   1040:   bfd_size_type ret;
                   1041:
                   1042:   symhdr = &debug->symbolic_header;
                   1043:   len = strlen (string);
1.1.1.2   christos 1044:   if (bfd_link_relocatable (info))
1.1       christos 1045:     {
                   1046:       if (!add_memory_shuffle (ainfo, &ainfo->ss, &ainfo->ss_end,
                   1047:                                (bfd_byte *) string, len + 1))
                   1048:        return -1;
                   1049:       ret = symhdr->issMax;
                   1050:       symhdr->issMax += len + 1;
                   1051:       fdr->cbSs += len + 1;
                   1052:     }
                   1053:   else
                   1054:     {
                   1055:       struct string_hash_entry *sh;
                   1056:
                   1057:       sh = string_hash_lookup (&ainfo->str_hash, string, TRUE, TRUE);
                   1058:       if (sh == (struct string_hash_entry *) NULL)
                   1059:        return -1;
                   1060:       if (sh->val == -1)
                   1061:        {
                   1062:          sh->val = symhdr->issMax;
                   1063:          symhdr->issMax += len + 1;
                   1064:          if (ainfo->ss_hash == (struct string_hash_entry *) NULL)
                   1065:            ainfo->ss_hash = sh;
                   1066:          if (ainfo->ss_hash_end
                   1067:              != (struct string_hash_entry *) NULL)
                   1068:            ainfo->ss_hash_end->next = sh;
                   1069:          ainfo->ss_hash_end = sh;
                   1070:        }
                   1071:       ret = sh->val;
                   1072:     }
                   1073:
                   1074:   return ret;
                   1075: }
                   1076:
                   1077: /* Add debugging information from a non-ECOFF file.  */
                   1078:
                   1079: bfd_boolean
                   1080: bfd_ecoff_debug_accumulate_other (void * handle,
                   1081:                                  bfd *output_bfd,
                   1082:                                  struct ecoff_debug_info *output_debug,
                   1083:                                  const struct ecoff_debug_swap *output_swap,
                   1084:                                  bfd *input_bfd,
                   1085:                                  struct bfd_link_info *info)
                   1086: {
                   1087:   struct accumulate *ainfo = (struct accumulate *) handle;
                   1088:   void (* const swap_sym_out) (bfd *, const SYMR *, void *)
                   1089:     = output_swap->swap_sym_out;
                   1090:   HDRR *output_symhdr = &output_debug->symbolic_header;
                   1091:   FDR fdr;
                   1092:   asection *sec;
                   1093:   asymbol **symbols;
                   1094:   asymbol **sym_ptr;
                   1095:   asymbol **sym_end;
                   1096:   long symsize;
                   1097:   long symcount;
                   1098:   void * external_fdr;
                   1099:
                   1100:   memset (&fdr, 0, sizeof fdr);
                   1101:
                   1102:   sec = bfd_get_section_by_name (input_bfd, ".text");
                   1103:   if (sec != NULL)
                   1104:     fdr.adr = sec->output_section->vma + sec->output_offset;
                   1105:   else
                   1106:     {
                   1107:       /* FIXME: What about .init or .fini?  */
                   1108:       fdr.adr = 0;
                   1109:     }
                   1110:
                   1111:   fdr.issBase = output_symhdr->issMax;
                   1112:   fdr.cbSs = 0;
                   1113:   fdr.rss = ecoff_add_string (ainfo, info, output_debug, &fdr,
                   1114:                              input_bfd->filename);
                   1115:   if (fdr.rss == -1)
                   1116:     return FALSE;
                   1117:   fdr.isymBase = output_symhdr->isymMax;
                   1118:
                   1119:   /* Get the local symbols from the input BFD.  */
                   1120:   symsize = bfd_get_symtab_upper_bound (input_bfd);
                   1121:   if (symsize < 0)
                   1122:     return FALSE;
                   1123:   symbols = (asymbol **) bfd_alloc (output_bfd, (bfd_size_type) symsize);
                   1124:   if (symbols == (asymbol **) NULL)
                   1125:     return FALSE;
                   1126:   symcount = bfd_canonicalize_symtab (input_bfd, symbols);
                   1127:   if (symcount < 0)
                   1128:     return FALSE;
                   1129:   sym_end = symbols + symcount;
                   1130:
                   1131:   /* Handle the local symbols.  Any external symbols are handled
                   1132:      separately.  */
                   1133:   fdr.csym = 0;
                   1134:   for (sym_ptr = symbols; sym_ptr != sym_end; sym_ptr++)
                   1135:     {
                   1136:       SYMR internal_sym;
                   1137:       void * external_sym;
                   1138:
                   1139:       if (((*sym_ptr)->flags & BSF_EXPORT) != 0)
                   1140:        continue;
                   1141:       memset (&internal_sym, 0, sizeof internal_sym);
                   1142:       internal_sym.iss = ecoff_add_string (ainfo, info, output_debug, &fdr,
                   1143:                                           (*sym_ptr)->name);
                   1144:
                   1145:       if (internal_sym.iss == -1)
                   1146:        return FALSE;
                   1147:       if (bfd_is_com_section ((*sym_ptr)->section)
                   1148:          || bfd_is_und_section ((*sym_ptr)->section))
                   1149:        internal_sym.value = (*sym_ptr)->value;
                   1150:       else
                   1151:        internal_sym.value = ((*sym_ptr)->value
                   1152:                              + (*sym_ptr)->section->output_offset
                   1153:                              + (*sym_ptr)->section->output_section->vma);
                   1154:       internal_sym.st = stNil;
                   1155:       internal_sym.sc = scUndefined;
                   1156:       internal_sym.index = indexNil;
                   1157:
                   1158:       external_sym = objalloc_alloc (ainfo->memory,
                   1159:                                     output_swap->external_sym_size);
                   1160:       if (!external_sym)
                   1161:        {
                   1162:          bfd_set_error (bfd_error_no_memory);
                   1163:          return FALSE;
                   1164:        }
                   1165:       (*swap_sym_out) (output_bfd, &internal_sym, external_sym);
                   1166:       add_memory_shuffle (ainfo, &ainfo->sym, &ainfo->sym_end,
                   1167:                          (bfd_byte *) external_sym,
                   1168:                          (unsigned long) output_swap->external_sym_size);
                   1169:       ++fdr.csym;
                   1170:       ++output_symhdr->isymMax;
                   1171:     }
                   1172:
                   1173:   bfd_release (output_bfd, symbols);
                   1174:
                   1175:   /* Leave everything else in the FDR zeroed out.  This will cause
                   1176:      the lang field to be langC.  The fBigendian field will
                   1177:      indicate little endian format, but it doesn't matter because
                   1178:      it only applies to aux fields and there are none.  */
                   1179:   external_fdr = objalloc_alloc (ainfo->memory,
                   1180:                                 output_swap->external_fdr_size);
                   1181:   if (!external_fdr)
                   1182:     {
                   1183:       bfd_set_error (bfd_error_no_memory);
                   1184:       return FALSE;
                   1185:     }
                   1186:   (*output_swap->swap_fdr_out) (output_bfd, &fdr, external_fdr);
                   1187:   add_memory_shuffle (ainfo, &ainfo->fdr, &ainfo->fdr_end,
                   1188:                      (bfd_byte *) external_fdr,
                   1189:                      (unsigned long) output_swap->external_fdr_size);
                   1190:
                   1191:   ++output_symhdr->ifdMax;
                   1192:
                   1193:   return TRUE;
                   1194: }
                   1195:
                   1196: /* Set up ECOFF debugging information for the external symbols.
                   1197:    FIXME: This is done using a memory buffer, but it should be
                   1198:    probably be changed to use a shuffle structure.  The assembler uses
                   1199:    this interface, so that must be changed to do something else.  */
                   1200:
                   1201: bfd_boolean
                   1202: bfd_ecoff_debug_externals (bfd *abfd,
                   1203:                           struct ecoff_debug_info *debug,
                   1204:                           const struct ecoff_debug_swap *swap,
                   1205:                           bfd_boolean relocatable,
                   1206:                           bfd_boolean (*get_extr) (asymbol *, EXTR *),
                   1207:                           void (*set_index) (asymbol *, bfd_size_type))
                   1208: {
                   1209:   HDRR * const symhdr = &debug->symbolic_header;
                   1210:   asymbol **sym_ptr_ptr;
                   1211:   size_t c;
                   1212:
                   1213:   sym_ptr_ptr = bfd_get_outsymbols (abfd);
                   1214:   if (sym_ptr_ptr == NULL)
                   1215:     return TRUE;
                   1216:
                   1217:   for (c = bfd_get_symcount (abfd); c > 0; c--, sym_ptr_ptr++)
                   1218:     {
                   1219:       asymbol *sym_ptr;
                   1220:       EXTR esym;
                   1221:
                   1222:       sym_ptr = *sym_ptr_ptr;
                   1223:
                   1224:       /* Get the external symbol information.  */
                   1225:       if (! (*get_extr) (sym_ptr, &esym))
                   1226:        continue;
                   1227:
                   1228:       /* If we're producing an executable, move common symbols into
                   1229:         bss.  */
                   1230:       if (! relocatable)
                   1231:        {
                   1232:          if (esym.asym.sc == scCommon)
                   1233:            esym.asym.sc = scBss;
                   1234:          else if (esym.asym.sc == scSCommon)
                   1235:            esym.asym.sc = scSBss;
                   1236:        }
                   1237:
                   1238:       if (bfd_is_com_section (sym_ptr->section)
                   1239:          || bfd_is_und_section (sym_ptr->section)
                   1240:          || sym_ptr->section->output_section == (asection *) NULL)
                   1241:        {
                   1242:          /* FIXME: gas does not keep the value of a small undefined
                   1243:             symbol in the symbol itself, because of relocation
                   1244:             problems.  */
                   1245:          if (esym.asym.sc != scSUndefined
                   1246:              || esym.asym.value == 0
                   1247:              || sym_ptr->value != 0)
                   1248:            esym.asym.value = sym_ptr->value;
                   1249:        }
                   1250:       else
                   1251:        esym.asym.value = (sym_ptr->value
                   1252:                           + sym_ptr->section->output_offset
                   1253:                           + sym_ptr->section->output_section->vma);
                   1254:
                   1255:       if (set_index)
                   1256:        (*set_index) (sym_ptr, (bfd_size_type) symhdr->iextMax);
                   1257:
                   1258:       if (! bfd_ecoff_debug_one_external (abfd, debug, swap,
                   1259:                                          sym_ptr->name, &esym))
                   1260:        return FALSE;
                   1261:     }
                   1262:
                   1263:   return TRUE;
                   1264: }
                   1265:
                   1266: /* Add a single external symbol to the debugging information.  */
                   1267:
                   1268: bfd_boolean
                   1269: bfd_ecoff_debug_one_external (bfd *abfd,
                   1270:                              struct ecoff_debug_info *debug,
                   1271:                              const struct ecoff_debug_swap *swap,
                   1272:                              const char *name,
                   1273:                              EXTR *esym)
                   1274: {
                   1275:   const bfd_size_type external_ext_size = swap->external_ext_size;
                   1276:   void (* const swap_ext_out) (bfd *, const EXTR *, void *)
                   1277:     = swap->swap_ext_out;
                   1278:   HDRR * const symhdr = &debug->symbolic_header;
                   1279:   size_t namelen;
                   1280:
                   1281:   namelen = strlen (name);
                   1282:
                   1283:   if ((size_t) (debug->ssext_end - debug->ssext)
                   1284:       < symhdr->issExtMax + namelen + 1)
                   1285:     {
                   1286:       if (! ecoff_add_bytes ((char **) &debug->ssext,
                   1287:                             (char **) &debug->ssext_end,
                   1288:                             symhdr->issExtMax + namelen + 1))
                   1289:        return FALSE;
                   1290:     }
                   1291:   if ((size_t) ((char *) debug->external_ext_end
                   1292:                - (char *) debug->external_ext)
                   1293:       < (symhdr->iextMax + 1) * external_ext_size)
                   1294:     {
                   1295:       char *external_ext = (char *) debug->external_ext;
                   1296:       char *external_ext_end = (char *) debug->external_ext_end;
                   1297:       if (! ecoff_add_bytes ((char **) &external_ext,
                   1298:                             (char **) &external_ext_end,
                   1299:                             (symhdr->iextMax + 1) * (size_t) external_ext_size))
                   1300:        return FALSE;
                   1301:       debug->external_ext = external_ext;
                   1302:       debug->external_ext_end = external_ext_end;
                   1303:     }
                   1304:
                   1305:   esym->asym.iss = symhdr->issExtMax;
                   1306:
                   1307:   (*swap_ext_out) (abfd, esym,
                   1308:                   ((char *) debug->external_ext
                   1309:                    + symhdr->iextMax * swap->external_ext_size));
                   1310:
                   1311:   ++symhdr->iextMax;
                   1312:
                   1313:   strcpy (debug->ssext + symhdr->issExtMax, name);
                   1314:   symhdr->issExtMax += namelen + 1;
                   1315:
                   1316:   return TRUE;
                   1317: }
                   1318:
                   1319: /* Align the ECOFF debugging information.  */
                   1320:
                   1321: static void
                   1322: ecoff_align_debug (bfd *abfd ATTRIBUTE_UNUSED,
                   1323:                   struct ecoff_debug_info *debug,
                   1324:                   const struct ecoff_debug_swap *swap)
                   1325: {
                   1326:   HDRR * const symhdr = &debug->symbolic_header;
                   1327:   bfd_size_type debug_align, aux_align, rfd_align;
                   1328:   size_t add;
                   1329:
                   1330:   /* Adjust the counts so that structures are aligned.  */
                   1331:   debug_align = swap->debug_align;
                   1332:   aux_align = debug_align / sizeof (union aux_ext);
                   1333:   rfd_align = debug_align / swap->external_rfd_size;
                   1334:
                   1335:   add = debug_align - (symhdr->cbLine & (debug_align - 1));
                   1336:   if (add != debug_align)
                   1337:     {
                   1338:       if (debug->line != (unsigned char *) NULL)
                   1339:        memset ((debug->line + symhdr->cbLine), 0, add);
                   1340:       symhdr->cbLine += add;
                   1341:     }
                   1342:
                   1343:   add = debug_align - (symhdr->issMax & (debug_align - 1));
                   1344:   if (add != debug_align)
                   1345:     {
                   1346:       if (debug->ss != (char *) NULL)
                   1347:        memset ((debug->ss + symhdr->issMax), 0, add);
                   1348:       symhdr->issMax += add;
                   1349:     }
                   1350:
                   1351:   add = debug_align - (symhdr->issExtMax & (debug_align - 1));
                   1352:   if (add != debug_align)
                   1353:     {
                   1354:       if (debug->ssext != (char *) NULL)
                   1355:        memset ((debug->ssext + symhdr->issExtMax), 0, add);
                   1356:       symhdr->issExtMax += add;
                   1357:     }
                   1358:
                   1359:   add = aux_align - (symhdr->iauxMax & (aux_align - 1));
                   1360:   if (add != aux_align)
                   1361:     {
                   1362:       if (debug->external_aux != (union aux_ext *) NULL)
                   1363:        memset ((debug->external_aux + symhdr->iauxMax), 0,
                   1364:                add * sizeof (union aux_ext));
                   1365:       symhdr->iauxMax += add;
                   1366:     }
                   1367:
                   1368:   add = rfd_align - (symhdr->crfd & (rfd_align - 1));
                   1369:   if (add != rfd_align)
                   1370:     {
                   1371:       if (debug->external_rfd != NULL)
                   1372:        memset (((char *) debug->external_rfd
                   1373:                 + symhdr->crfd * swap->external_rfd_size),
                   1374:                0, (size_t) (add * swap->external_rfd_size));
                   1375:       symhdr->crfd += add;
                   1376:     }
                   1377: }
                   1378:
                   1379: /* Return the size required by the ECOFF debugging information.  */
                   1380:
                   1381: bfd_size_type
                   1382: bfd_ecoff_debug_size (bfd *abfd,
                   1383:                      struct ecoff_debug_info *debug,
                   1384:                      const struct ecoff_debug_swap *swap)
                   1385: {
                   1386:   bfd_size_type tot;
                   1387:
                   1388:   ecoff_align_debug (abfd, debug, swap);
                   1389:   tot = swap->external_hdr_size;
                   1390:
                   1391: #define ADD(count, size) \
                   1392:   tot += debug->symbolic_header.count * size
                   1393:
                   1394:   ADD (cbLine, sizeof (unsigned char));
                   1395:   ADD (idnMax, swap->external_dnr_size);
                   1396:   ADD (ipdMax, swap->external_pdr_size);
                   1397:   ADD (isymMax, swap->external_sym_size);
                   1398:   ADD (ioptMax, swap->external_opt_size);
                   1399:   ADD (iauxMax, sizeof (union aux_ext));
                   1400:   ADD (issMax, sizeof (char));
                   1401:   ADD (issExtMax, sizeof (char));
                   1402:   ADD (ifdMax, swap->external_fdr_size);
                   1403:   ADD (crfd, swap->external_rfd_size);
                   1404:   ADD (iextMax, swap->external_ext_size);
                   1405:
                   1406: #undef ADD
                   1407:
                   1408:   return tot;
                   1409: }
                   1410:
                   1411: /* Write out the ECOFF symbolic header, given the file position it is
                   1412:    going to be placed at.  This assumes that the counts are set
                   1413:    correctly.  */
                   1414:
                   1415: static bfd_boolean
                   1416: ecoff_write_symhdr (bfd *abfd,
                   1417:                    struct ecoff_debug_info *debug,
                   1418:                    const struct ecoff_debug_swap *swap,
                   1419:                    file_ptr where)
                   1420: {
                   1421:   HDRR * const symhdr = &debug->symbolic_header;
                   1422:   char *buff = NULL;
                   1423:
                   1424:   ecoff_align_debug (abfd, debug, swap);
                   1425:
                   1426:   /* Go to the right location in the file.  */
                   1427:   if (bfd_seek (abfd, where, SEEK_SET) != 0)
                   1428:     return FALSE;
                   1429:
                   1430:   where += swap->external_hdr_size;
                   1431:
                   1432:   symhdr->magic = swap->sym_magic;
                   1433:
                   1434:   /* Fill in the file offsets.  */
                   1435: #define SET(offset, count, size) \
                   1436:   if (symhdr->count == 0) \
                   1437:     symhdr->offset = 0; \
                   1438:   else \
                   1439:     { \
                   1440:       symhdr->offset = where; \
                   1441:       where += symhdr->count * size; \
                   1442:     }
                   1443:
                   1444:   SET (cbLineOffset, cbLine, sizeof (unsigned char));
                   1445:   SET (cbDnOffset, idnMax, swap->external_dnr_size);
                   1446:   SET (cbPdOffset, ipdMax, swap->external_pdr_size);
                   1447:   SET (cbSymOffset, isymMax, swap->external_sym_size);
                   1448:   SET (cbOptOffset, ioptMax, swap->external_opt_size);
                   1449:   SET (cbAuxOffset, iauxMax, sizeof (union aux_ext));
                   1450:   SET (cbSsOffset, issMax, sizeof (char));
                   1451:   SET (cbSsExtOffset, issExtMax, sizeof (char));
                   1452:   SET (cbFdOffset, ifdMax, swap->external_fdr_size);
                   1453:   SET (cbRfdOffset, crfd, swap->external_rfd_size);
                   1454:   SET (cbExtOffset, iextMax, swap->external_ext_size);
                   1455: #undef SET
                   1456:
                   1457:   buff = (char *) bfd_malloc (swap->external_hdr_size);
                   1458:   if (buff == NULL && swap->external_hdr_size != 0)
                   1459:     goto error_return;
                   1460:
                   1461:   (*swap->swap_hdr_out) (abfd, symhdr, buff);
                   1462:   if (bfd_bwrite (buff, swap->external_hdr_size, abfd)
                   1463:       != swap->external_hdr_size)
                   1464:     goto error_return;
                   1465:
                   1466:   if (buff != NULL)
                   1467:     free (buff);
                   1468:   return TRUE;
                   1469:  error_return:
                   1470:   if (buff != NULL)
                   1471:     free (buff);
                   1472:   return FALSE;
                   1473: }
                   1474:
                   1475: /* Write out the ECOFF debugging information.  This function assumes
                   1476:    that the information (the pointers and counts) in *DEBUG have been
                   1477:    set correctly.  WHERE is the position in the file to write the
                   1478:    information to.  This function fills in the file offsets in the
                   1479:    symbolic header.  */
                   1480:
                   1481: bfd_boolean
                   1482: bfd_ecoff_write_debug (bfd *abfd,
                   1483:                       struct ecoff_debug_info *debug,
                   1484:                       const struct ecoff_debug_swap *swap,
                   1485:                       file_ptr where)
                   1486: {
                   1487:   HDRR * const symhdr = &debug->symbolic_header;
                   1488:
                   1489:   if (! ecoff_write_symhdr (abfd, debug, swap, where))
                   1490:     return FALSE;
                   1491:
                   1492: #define WRITE(ptr, count, size, offset) \
                   1493:   BFD_ASSERT (symhdr->offset == 0 \
                   1494:              || (bfd_vma) bfd_tell (abfd) == symhdr->offset); \
                   1495:   if (bfd_bwrite (debug->ptr, (bfd_size_type) size * symhdr->count, abfd)\
                   1496:       != size * symhdr->count) \
                   1497:     return FALSE;
                   1498:
                   1499:   WRITE (line, cbLine, sizeof (unsigned char), cbLineOffset);
                   1500:   WRITE (external_dnr, idnMax, swap->external_dnr_size, cbDnOffset);
                   1501:   WRITE (external_pdr, ipdMax, swap->external_pdr_size, cbPdOffset);
                   1502:   WRITE (external_sym, isymMax, swap->external_sym_size, cbSymOffset);
                   1503:   WRITE (external_opt, ioptMax, swap->external_opt_size, cbOptOffset);
                   1504:   WRITE (external_aux, iauxMax, (bfd_size_type) sizeof (union aux_ext),
                   1505:         cbAuxOffset);
                   1506:   WRITE (ss, issMax, sizeof (char), cbSsOffset);
                   1507:   WRITE (ssext, issExtMax, sizeof (char), cbSsExtOffset);
                   1508:   WRITE (external_fdr, ifdMax, swap->external_fdr_size, cbFdOffset);
                   1509:   WRITE (external_rfd, crfd, swap->external_rfd_size, cbRfdOffset);
                   1510:   WRITE (external_ext, iextMax, swap->external_ext_size, cbExtOffset);
                   1511: #undef WRITE
                   1512:
                   1513:   return TRUE;
                   1514: }
                   1515:
                   1516: /* Write out a shuffle list.  */
                   1517:
                   1518:
                   1519: static bfd_boolean
                   1520: ecoff_write_shuffle (bfd *abfd,
                   1521:                     const struct ecoff_debug_swap *swap,
                   1522:                     struct shuffle *shuffle,
                   1523:                     void * space)
                   1524: {
                   1525:   struct shuffle *l;
                   1526:   unsigned long total;
                   1527:
                   1528:   total = 0;
                   1529:   for (l = shuffle; l != (struct shuffle *) NULL; l = l->next)
                   1530:     {
                   1531:       if (! l->filep)
                   1532:        {
                   1533:          if (bfd_bwrite (l->u.memory, (bfd_size_type) l->size, abfd)
                   1534:              != l->size)
                   1535:            return FALSE;
                   1536:        }
                   1537:       else
                   1538:        {
                   1539:          if (bfd_seek (l->u.file.input_bfd, l->u.file.offset, SEEK_SET) != 0
                   1540:              || bfd_bread (space, (bfd_size_type) l->size,
                   1541:                           l->u.file.input_bfd) != l->size
                   1542:              || bfd_bwrite (space, (bfd_size_type) l->size, abfd) != l->size)
                   1543:            return FALSE;
                   1544:        }
                   1545:       total += l->size;
                   1546:     }
                   1547:
                   1548:   if ((total & (swap->debug_align - 1)) != 0)
                   1549:     {
                   1550:       unsigned int i;
                   1551:       bfd_byte *s;
                   1552:
                   1553:       i = swap->debug_align - (total & (swap->debug_align - 1));
                   1554:       s = (bfd_byte *) bfd_zmalloc ((bfd_size_type) i);
                   1555:       if (s == NULL && i != 0)
                   1556:        return FALSE;
                   1557:
                   1558:       if (bfd_bwrite (s, (bfd_size_type) i, abfd) != i)
                   1559:        {
                   1560:          free (s);
                   1561:          return FALSE;
                   1562:        }
                   1563:       free (s);
                   1564:     }
                   1565:
                   1566:   return TRUE;
                   1567: }
                   1568:
                   1569: /* Write out debugging information using accumulated linker
                   1570:    information.  */
                   1571:
                   1572: bfd_boolean
                   1573: bfd_ecoff_write_accumulated_debug (void * handle,
                   1574:                                   bfd *abfd,
                   1575:                                   struct ecoff_debug_info *debug,
                   1576:                                   const struct ecoff_debug_swap *swap,
                   1577:                                   struct bfd_link_info *info,
                   1578:                                   file_ptr where)
                   1579: {
                   1580:   struct accumulate *ainfo = (struct accumulate *) handle;
                   1581:   void * space = NULL;
                   1582:   bfd_size_type amt;
                   1583:
                   1584:   if (! ecoff_write_symhdr (abfd, debug, swap, where))
                   1585:     goto error_return;
                   1586:
                   1587:   amt = ainfo->largest_file_shuffle;
                   1588:   space = bfd_malloc (amt);
                   1589:   if (space == NULL && ainfo->largest_file_shuffle != 0)
                   1590:     goto error_return;
                   1591:
                   1592:   if (! ecoff_write_shuffle (abfd, swap, ainfo->line, space)
                   1593:       || ! ecoff_write_shuffle (abfd, swap, ainfo->pdr, space)
                   1594:       || ! ecoff_write_shuffle (abfd, swap, ainfo->sym, space)
                   1595:       || ! ecoff_write_shuffle (abfd, swap, ainfo->opt, space)
                   1596:       || ! ecoff_write_shuffle (abfd, swap, ainfo->aux, space))
                   1597:     goto error_return;
                   1598:
                   1599:   /* The string table is written out from the hash table if this is a
                   1600:      final link.  */
1.1.1.2   christos 1601:   if (bfd_link_relocatable (info))
1.1       christos 1602:     {
                   1603:       BFD_ASSERT (ainfo->ss_hash == (struct string_hash_entry *) NULL);
                   1604:       if (! ecoff_write_shuffle (abfd, swap, ainfo->ss, space))
                   1605:        goto error_return;
                   1606:     }
                   1607:   else
                   1608:     {
                   1609:       unsigned long total;
                   1610:       bfd_byte null;
                   1611:       struct string_hash_entry *sh;
                   1612:
                   1613:       BFD_ASSERT (ainfo->ss == (struct shuffle *) NULL);
                   1614:       null = 0;
                   1615:       if (bfd_bwrite (&null, (bfd_size_type) 1, abfd) != 1)
                   1616:        goto error_return;
                   1617:       total = 1;
                   1618:       BFD_ASSERT (ainfo->ss_hash == NULL || ainfo->ss_hash->val == 1);
                   1619:       for (sh = ainfo->ss_hash;
                   1620:           sh != (struct string_hash_entry *) NULL;
                   1621:           sh = sh->next)
                   1622:        {
                   1623:          size_t len;
                   1624:
                   1625:          len = strlen (sh->root.string);
                   1626:          amt = len + 1;
                   1627:          if (bfd_bwrite (sh->root.string, amt, abfd) != amt)
                   1628:            goto error_return;
                   1629:          total += len + 1;
                   1630:        }
                   1631:
                   1632:       if ((total & (swap->debug_align - 1)) != 0)
                   1633:        {
                   1634:          unsigned int i;
                   1635:          bfd_byte *s;
                   1636:
                   1637:          i = swap->debug_align - (total & (swap->debug_align - 1));
                   1638:          s = (bfd_byte *) bfd_zmalloc ((bfd_size_type) i);
                   1639:          if (s == NULL && i != 0)
                   1640:            goto error_return;
                   1641:
                   1642:          if (bfd_bwrite (s, (bfd_size_type) i, abfd) != i)
                   1643:            {
                   1644:              free (s);
                   1645:              goto error_return;
                   1646:            }
                   1647:          free (s);
                   1648:        }
                   1649:     }
                   1650:
                   1651:   /* The external strings and symbol are not converted over to using
                   1652:      shuffles.  FIXME: They probably should be.  */
                   1653:   amt = debug->symbolic_header.issExtMax;
                   1654:   if (bfd_bwrite (debug->ssext, amt, abfd) != amt)
                   1655:     goto error_return;
                   1656:   if ((debug->symbolic_header.issExtMax & (swap->debug_align - 1)) != 0)
                   1657:     {
                   1658:       unsigned int i;
                   1659:       bfd_byte *s;
                   1660:
                   1661:       i = (swap->debug_align
                   1662:           - (debug->symbolic_header.issExtMax & (swap->debug_align - 1)));
                   1663:       s = (bfd_byte *) bfd_zmalloc ((bfd_size_type) i);
                   1664:       if (s == NULL && i != 0)
                   1665:        goto error_return;
                   1666:
                   1667:       if (bfd_bwrite (s, (bfd_size_type) i, abfd) != i)
                   1668:        {
                   1669:          free (s);
                   1670:          goto error_return;
                   1671:        }
                   1672:       free (s);
                   1673:     }
                   1674:
                   1675:   if (! ecoff_write_shuffle (abfd, swap, ainfo->fdr, space)
                   1676:       || ! ecoff_write_shuffle (abfd, swap, ainfo->rfd, space))
                   1677:     goto error_return;
                   1678:
                   1679:   BFD_ASSERT (debug->symbolic_header.cbExtOffset == 0
                   1680:              || (debug->symbolic_header.cbExtOffset
                   1681:                  == (bfd_vma) bfd_tell (abfd)));
                   1682:
                   1683:   amt = debug->symbolic_header.iextMax * swap->external_ext_size;
                   1684:   if (bfd_bwrite (debug->external_ext, amt, abfd) != amt)
                   1685:     goto error_return;
                   1686:
                   1687:   if (space != NULL)
                   1688:     free (space);
                   1689:   return TRUE;
                   1690:
                   1691:  error_return:
                   1692:   if (space != NULL)
                   1693:     free (space);
                   1694:   return FALSE;
                   1695: }
                   1696: 
                   1697: /* Handle the find_nearest_line function for both ECOFF and MIPS ELF
                   1698:    files.  */
                   1699:
                   1700: /* Compare FDR entries.  This is called via qsort.  */
                   1701:
                   1702: static int
                   1703: cmp_fdrtab_entry (const void * leftp, const void * rightp)
                   1704: {
                   1705:   const struct ecoff_fdrtab_entry *lp =
                   1706:     (const struct ecoff_fdrtab_entry *) leftp;
                   1707:   const struct ecoff_fdrtab_entry *rp =
                   1708:     (const struct ecoff_fdrtab_entry *) rightp;
                   1709:
                   1710:   if (lp->base_addr < rp->base_addr)
                   1711:     return -1;
                   1712:   if (lp->base_addr > rp->base_addr)
                   1713:     return 1;
                   1714:   return 0;
                   1715: }
                   1716:
                   1717: /* Each file descriptor (FDR) has a memory address, to simplify
                   1718:    looking up an FDR by address, we build a table covering all FDRs
                   1719:    that have a least one procedure descriptor in them.  The final
                   1720:    table will be sorted by address so we can look it up via binary
                   1721:    search.  */
                   1722:
                   1723: static bfd_boolean
                   1724: mk_fdrtab (bfd *abfd,
                   1725:           struct ecoff_debug_info * const debug_info,
                   1726:           const struct ecoff_debug_swap * const debug_swap,
                   1727:           struct ecoff_find_line *line_info)
                   1728: {
                   1729:   struct ecoff_fdrtab_entry *tab;
                   1730:   FDR *fdr_ptr;
                   1731:   FDR *fdr_start;
                   1732:   FDR *fdr_end;
                   1733:   bfd_boolean stabs;
                   1734:   long len;
                   1735:   bfd_size_type amt;
                   1736:
                   1737:   fdr_start = debug_info->fdr;
                   1738:   fdr_end = fdr_start + debug_info->symbolic_header.ifdMax;
                   1739:
                   1740:   /* First, let's see how long the table needs to be.  */
                   1741:   for (len = 0, fdr_ptr = fdr_start; fdr_ptr < fdr_end; fdr_ptr++)
                   1742:     {
                   1743:       if (fdr_ptr->cpd == 0)   /* Skip FDRs that have no PDRs.  */
                   1744:        continue;
                   1745:       ++len;
                   1746:     }
                   1747:
                   1748:   /* Now, create and fill in the table.  */
                   1749:   amt = (bfd_size_type) len * sizeof (struct ecoff_fdrtab_entry);
                   1750:   line_info->fdrtab = (struct ecoff_fdrtab_entry*) bfd_zalloc (abfd, amt);
                   1751:   if (line_info->fdrtab == NULL)
                   1752:     return FALSE;
                   1753:   line_info->fdrtab_len = len;
                   1754:
                   1755:   tab = line_info->fdrtab;
                   1756:   for (fdr_ptr = fdr_start; fdr_ptr < fdr_end; fdr_ptr++)
                   1757:     {
                   1758:       if (fdr_ptr->cpd == 0)
                   1759:        continue;
                   1760:
                   1761:       /* Check whether this file has stabs debugging information.  In
                   1762:         a file with stabs debugging information, the second local
                   1763:         symbol is named @stabs.  */
                   1764:       stabs = FALSE;
                   1765:       if (fdr_ptr->csym >= 2)
                   1766:        {
                   1767:          char *sym_ptr;
                   1768:          SYMR sym;
                   1769:
                   1770:          sym_ptr = ((char *) debug_info->external_sym
                   1771:                     + (fdr_ptr->isymBase + 1) * debug_swap->external_sym_size);
                   1772:          (*debug_swap->swap_sym_in) (abfd, sym_ptr, &sym);
                   1773:          if (strcmp (debug_info->ss + fdr_ptr->issBase + sym.iss,
                   1774:                      STABS_SYMBOL) == 0)
                   1775:            stabs = TRUE;
                   1776:        }
                   1777:
                   1778:       if (!stabs)
                   1779:        {
                   1780:          /* eraxxon: There are at least two problems with this computation:
                   1781:             1) PDRs do *not* contain offsets but full vma's; and typically the
                   1782:             address of the first PDR is the address of the FDR, which will
                   1783:             make (most) of the results of the original computation 0!
                   1784:             2) Once in a wacky while, the Compaq compiler generated PDR
                   1785:             addresses do not equal the FDR vma, but they (the PDR address)
                   1786:             are still vma's and not offsets.  Cf. comments in
                   1787:             'lookup_line'.  */
                   1788:          /* The address of the first PDR is the offset of that
                   1789:             procedure relative to the beginning of file FDR.  */
1.1.1.2   christos 1790:          tab->base_addr = fdr_ptr->adr;
1.1       christos 1791:        }
                   1792:       else
                   1793:        {
                   1794:          /* XXX I don't know about stabs, so this is a guess
                   1795:             (davidm@cs.arizona.edu).  */
                   1796:          tab->base_addr = fdr_ptr->adr;
                   1797:        }
                   1798:       tab->fdr = fdr_ptr;
                   1799:       ++tab;
                   1800:     }
                   1801:
                   1802:   /* Finally, the table is sorted in increasing memory-address order.
                   1803:      The table is mostly sorted already, but there are cases (e.g.,
                   1804:      static functions in include files), where this does not hold.
                   1805:      Use "odump -PFv" to verify...  */
                   1806:   qsort (line_info->fdrtab, (size_t) len,
                   1807:         sizeof (struct ecoff_fdrtab_entry), cmp_fdrtab_entry);
                   1808:
                   1809:   return TRUE;
                   1810: }
                   1811:
                   1812: /* Return index of first FDR that covers to OFFSET.  */
                   1813:
                   1814: static long
                   1815: fdrtab_lookup (struct ecoff_find_line *line_info, bfd_vma offset)
                   1816: {
                   1817:   long low, high, len;
                   1818:   long mid = -1;
                   1819:   struct ecoff_fdrtab_entry *tab;
                   1820:
                   1821:   len = line_info->fdrtab_len;
                   1822:   if (len == 0)
                   1823:     return -1;
                   1824:
                   1825:   tab = line_info->fdrtab;
                   1826:   for (low = 0, high = len - 1 ; low != high ;)
                   1827:     {
                   1828:       mid = (high + low) / 2;
                   1829:       if (offset >= tab[mid].base_addr && offset < tab[mid + 1].base_addr)
                   1830:        goto find_min;
                   1831:
                   1832:       if (tab[mid].base_addr > offset)
                   1833:        high = mid;
                   1834:       else
                   1835:        low = mid + 1;
                   1836:     }
                   1837:
                   1838:   /* eraxxon: at this point 'offset' is either lower than the lowest entry or
                   1839:      higher than the highest entry. In the former case high = low = mid = 0;
                   1840:      we want to return -1.  In the latter case, low = high and mid = low - 1;
                   1841:      we want to return the index of the highest entry.  Only in former case
                   1842:      will the following 'catch-all' test be true.  */
                   1843:   ++mid;
                   1844:
                   1845:   /* Last entry is catch-all for all higher addresses.  */
                   1846:   if (offset < tab[mid].base_addr)
                   1847:     return -1;
                   1848:
                   1849:  find_min:
                   1850:
                   1851:   /* eraxxon: There may be multiple FDRs in the table with the
                   1852:      same base_addr; make sure that we are at the first one.  */
                   1853:   while (mid > 0 && tab[mid - 1].base_addr == tab[mid].base_addr)
                   1854:     --mid;
                   1855:
                   1856:   return mid;
                   1857: }
                   1858:
                   1859: /* Look up a line given an address, storing the information in
                   1860:    LINE_INFO->cache.  */
                   1861:
                   1862: static bfd_boolean
                   1863: lookup_line (bfd *abfd,
                   1864:             struct ecoff_debug_info * const debug_info,
                   1865:             const struct ecoff_debug_swap * const debug_swap,
                   1866:             struct ecoff_find_line *line_info)
                   1867: {
                   1868:   struct ecoff_fdrtab_entry *tab;
                   1869:   bfd_vma offset;
                   1870:   bfd_boolean stabs;
                   1871:   FDR *fdr_ptr;
                   1872:   int i;
                   1873:
                   1874:   /* eraxxon: note that 'offset' is the full vma, not a section offset.  */
                   1875:   offset = line_info->cache.start;
                   1876:
                   1877:   /* Build FDR table (sorted by object file's base-address) if we
                   1878:      don't have it already.  */
                   1879:   if (line_info->fdrtab == NULL
                   1880:       && !mk_fdrtab (abfd, debug_info, debug_swap, line_info))
                   1881:     return FALSE;
                   1882:
                   1883:   tab = line_info->fdrtab;
                   1884:
                   1885:   /* Find first FDR for address OFFSET.  */
                   1886:   i = fdrtab_lookup (line_info, offset);
                   1887:   if (i < 0)
                   1888:     return FALSE;              /* no FDR, no fun...  */
1.1.1.2   christos 1889:
1.1       christos 1890:   /* eraxxon: 'fdrtab_lookup' doesn't give what we want, at least for Compaq's
                   1891:      C++ compiler 6.2.  Consider three FDRs with starting addresses of x, y,
                   1892:      and z, respectively, such that x < y < z.  Assume further that
                   1893:      y < 'offset' < z.  It is possible at times that the PDR for 'offset' is
                   1894:      associated with FDR x and *not* with FDR y.  Erg!!
                   1895:
                   1896:      From a binary dump of my C++ test case 'moo' using Compaq's coffobjanl
                   1897:      (output format has been edited for our purposes):
                   1898:
                   1899:      FDR [2]: (main.C): First instruction: 0x12000207c <x>
                   1900:        PDR [5] for File [2]: LoopTest__Xv                 <0x1200020a0> (a)
                   1901:        PDR [7] for File [2]: foo__Xv                      <0x120002168>
                   1902:      FDR [1]: (-1):     First instruction: 0x1200020e8 <y>
                   1903:        PDR [3] for File [1]:                              <0x120001ad0> (b)
                   1904:      FDR [6]: (-1):     First instruction: 0x1200026f0 <z>
                   1905:
                   1906:      (a) In the case of PDR5, the vma is such that the first few instructions
                   1907:      of the procedure can be found.  But since the size of this procedure is
                   1908:      160b, the vma will soon cross into the 'address space' of FDR1 and no
                   1909:      debugging info will be found.  How repugnant!
                   1910:
                   1911:      (b) It is also possible for a PDR to have a *lower* vma than its associated
                   1912:      FDR; see FDR1 and PDR3.  Gross!
                   1913:
                   1914:      Since the FDRs that are causing so much havok (in this case) 1) do not
                   1915:      describe actual files (fdr.rss == -1), and 2) contain only compiler
                   1916:      generated routines, I thought a simple fix would be to exclude them from
                   1917:      the FDR table in 'mk_fdrtab'.  But, besides not knowing for certain
                   1918:      whether this would be correct, it creates an additional problem.  If we
                   1919:      happen to ask for source file info on a compiler generated (procedure)
                   1920:      symbol -- which is still in the symbol table -- the result can be
                   1921:      information from a real procedure!  This is because compiler generated
                   1922:      procedures with vma's higher than the last FDR in the fdr table will be
                   1923:      associated with a PDR from this FDR, specifically the PDR with the
                   1924:      highest vma.  This wasn't a problem before, because each procedure had a
                   1925:      PDR.  (Yes, this problem could be eliminated if we kept the size of the
                   1926:      last PDR around, but things are already getting ugly).
                   1927:
                   1928:      Probably, a better solution would be to have a sorted PDR table.  Each
                   1929:      PDR would have a pointer to its FDR so file information could still be
                   1930:      obtained.  A FDR table could still be constructed if necessary -- since
                   1931:      it only contains pointers, not much extra memory would be used -- but
                   1932:      the PDR table would be searched to locate debugging info.
                   1933:
                   1934:      There is still at least one remaining issue.  Sometimes a FDR can have a
                   1935:      bogus name, but contain PDRs that should belong to another FDR with a
                   1936:      real name.  E.g:
                   1937:
                   1938:      FDR [3]: 0000000120001b50 (/home/.../Array.H~alt~deccxx_5E5A62AD)
                   1939:        PDR [a] for File [3]: 0000000120001b50
                   1940:        PDR [b] for File [3]: 0000000120001cf0
                   1941:        PDR [c] for File [3]: 0000000120001dc8
                   1942:        PDR [d] for File [3]: 0000000120001e40
                   1943:        PDR [e] for File [3]: 0000000120001eb8
                   1944:        PDR [f] for File [3]: 0000000120001f4c
                   1945:      FDR [4]: 0000000120001b50 (/home/.../Array.H)
                   1946:
                   1947:      Here, FDR4 has the correct name, but should (seemingly) contain PDRa-f.
                   1948:      The symbol table for PDR4 does contain symbols for PDRa-f, but so does
                   1949:      the symbol table for FDR3.  However the former is different; perhaps this
                   1950:      can be detected easily. (I'm not sure at this point.)  This problem only
                   1951:      seems to be associated with files with templates.  I am assuming the idea
                   1952:      is that there is a 'fake' FDR (with PDRs) for each differently typed set
                   1953:      of templates that must be generated.  Currently, FDR4 is completely
                   1954:      excluded from the FDR table in 'mk_fdrtab' because it contains no PDRs.
                   1955:
                   1956:      Since I don't have time to prepare a real fix for this right now, be
                   1957:      prepared for 'A Horrible Hack' to force the inspection of all non-stabs
                   1958:      FDRs.  It's coming...  */
                   1959:   fdr_ptr = tab[i].fdr;
                   1960:
                   1961:   /* Check whether this file has stabs debugging information.  In a
                   1962:      file with stabs debugging information, the second local symbol is
                   1963:      named @stabs.  */
                   1964:   stabs = FALSE;
                   1965:   if (fdr_ptr->csym >= 2)
                   1966:     {
                   1967:       char *sym_ptr;
                   1968:       SYMR sym;
                   1969:
                   1970:       sym_ptr = ((char *) debug_info->external_sym
                   1971:                 + (fdr_ptr->isymBase + 1) * debug_swap->external_sym_size);
                   1972:       (*debug_swap->swap_sym_in) (abfd, sym_ptr, &sym);
                   1973:       if (strcmp (debug_info->ss + fdr_ptr->issBase + sym.iss,
                   1974:                  STABS_SYMBOL) == 0)
                   1975:        stabs = TRUE;
                   1976:     }
                   1977:
                   1978:   if (!stabs)
                   1979:     {
                   1980:       bfd_size_type external_pdr_size;
                   1981:       char *pdr_ptr;
                   1982:       char *best_pdr = NULL;
                   1983:       FDR *best_fdr;
                   1984:       bfd_signed_vma best_dist = -1;
                   1985:       PDR pdr;
                   1986:       unsigned char *line_ptr;
                   1987:       unsigned char *line_end;
                   1988:       int lineno;
                   1989:       /* This file uses ECOFF debugging information.  Each FDR has a
                   1990:          list of procedure descriptors (PDR).  The address in the FDR
                   1991:          is the absolute address of the first procedure.  The address
                   1992:          in the first PDR gives the offset of that procedure relative
                   1993:          to the object file's base-address.  The addresses in
                   1994:          subsequent PDRs specify each procedure's address relative to
                   1995:          the object file's base-address.  To make things more juicy,
                   1996:          whenever the PROF bit in the PDR is set, the real entry point
                   1997:          of the procedure may be 16 bytes below what would normally be
                   1998:          the procedure's entry point.  Instead, DEC came up with a
                   1999:          wicked scheme to create profiled libraries "on the fly":
                   2000:          instead of shipping a regular and a profiled version of each
                   2001:          library, they insert 16 bytes of unused space in front of
                   2002:          each procedure and set the "prof" bit in the PDR to indicate
                   2003:          that there is a gap there (this is done automagically by "as"
                   2004:          when option "-pg" is specified).  Thus, normally, you link
                   2005:          against such a library and, except for lots of 16 byte gaps
                   2006:          between functions, things will behave as usual.  However,
                   2007:          when invoking "ld" with option "-pg", it will fill those gaps
                   2008:          with code that calls mcount().  It then moves the function's
                   2009:          entry point down by 16 bytes, and out pops a binary that has
                   2010:          all functions profiled.
                   2011:
                   2012:          NOTE: Neither FDRs nor PDRs are strictly sorted in memory
                   2013:                order.  For example, when including header-files that
                   2014:                define functions, the FDRs follow behind the including
                   2015:                file, even though their code may have been generated at
                   2016:                a lower address.  File coff-alpha.c from libbfd
                   2017:                illustrates this (use "odump -PFv" to look at a file's
                   2018:                FDR/PDR).  Similarly, PDRs are sometimes out of order
                   2019:                as well.  An example of this is OSF/1 v3.0 libc's
                   2020:                malloc.c.  I'm not sure why this happens, but it could
                   2021:                be due to optimizations that reorder a function's
                   2022:                position within an object-file.
                   2023:
                   2024:          Strategy:
                   2025:
                   2026:          On the first call to this function, we build a table of FDRs
                   2027:          that is sorted by the base-address of the object-file the FDR
                   2028:          is referring to.  Notice that each object-file may contain
                   2029:          code from multiple source files (e.g., due to code defined in
                   2030:          include files).  Thus, for any given base-address, there may
                   2031:          be multiple FDRs (but this case is, fortunately, uncommon).
                   2032:          lookup(addr) guarantees to return the first FDR that applies
                   2033:          to address ADDR.  Thus, after invoking lookup(), we have a
                   2034:          list of FDRs that may contain the PDR for ADDR.  Next, we
                   2035:          walk through the PDRs of these FDRs and locate the one that
                   2036:          is closest to ADDR (i.e., for which the difference between
                   2037:          ADDR and the PDR's entry point is positive and minimal).
                   2038:          Once, the right FDR and PDR are located, we simply walk
                   2039:          through the line-number table to lookup the line-number that
                   2040:          best matches ADDR.  Obviously, things could be sped up by
                   2041:          keeping a sorted list of PDRs instead of a sorted list of
                   2042:          FDRs.  However, this would increase space requirements
                   2043:          considerably, which is undesirable.  */
                   2044:       external_pdr_size = debug_swap->external_pdr_size;
                   2045:
                   2046:       /* eraxxon: The Horrible Hack: Because of the problems above, set 'i'
                   2047:         to 0 so we look through all FDRs.
                   2048:
                   2049:         Because FDR's without any symbols are assumed to be non-stabs,
                   2050:         searching through all FDRs may cause the following code to try to
                   2051:         read stabs FDRs as ECOFF ones.  However, I don't think this will
                   2052:         harm anything.  */
                   2053:       i = 0;
1.1.1.2   christos 2054:
1.1       christos 2055:       /* Search FDR list starting at tab[i] for the PDR that best matches
                   2056:          OFFSET.  Normally, the FDR list is only one entry long.  */
                   2057:       best_fdr = NULL;
                   2058:       do
                   2059:        {
                   2060:          /* eraxxon: 'dist' and 'min_dist' can be negative now
                   2061:              because we iterate over every FDR rather than just ones
                   2062:              with a base address less than or equal to 'offset'.  */
                   2063:          bfd_signed_vma dist = -1, min_dist = -1;
                   2064:          char *pdr_hold;
                   2065:          char *pdr_end;
                   2066:
                   2067:          fdr_ptr = tab[i].fdr;
                   2068:
                   2069:          pdr_ptr = ((char *) debug_info->external_pdr
                   2070:                     + fdr_ptr->ipdFirst * external_pdr_size);
                   2071:          pdr_end = pdr_ptr + fdr_ptr->cpd * external_pdr_size;
                   2072:          (*debug_swap->swap_pdr_in) (abfd, pdr_ptr, &pdr);
                   2073:          /* Find PDR that is closest to OFFSET.  If pdr.prof is set,
                   2074:             the procedure entry-point *may* be 0x10 below pdr.adr.  We
                   2075:             simply pretend that pdr.prof *implies* a lower entry-point.
                   2076:             This is safe because it just means that may identify 4 NOPs
                   2077:             in front of the function as belonging to the function.  */
                   2078:          for (pdr_hold = NULL;
                   2079:               pdr_ptr < pdr_end;
                   2080:               (pdr_ptr += external_pdr_size,
                   2081:                (*debug_swap->swap_pdr_in) (abfd, pdr_ptr, &pdr)))
                   2082:            {
                   2083:              if (offset >= (pdr.adr - 0x10 * pdr.prof))
                   2084:                {
                   2085:                  dist = offset - (pdr.adr - 0x10 * pdr.prof);
                   2086:
                   2087:                  /* eraxxon: 'dist' can be negative now.  Note that
                   2088:                      'min_dist' can be negative if 'pdr_hold' below is NULL.  */
                   2089:                  if (!pdr_hold || (dist >= 0 && dist < min_dist))
                   2090:                    {
                   2091:                      min_dist = dist;
                   2092:                      pdr_hold = pdr_ptr;
                   2093:                    }
                   2094:                }
                   2095:            }
                   2096:
                   2097:          if (!best_pdr || (min_dist >= 0 && min_dist < best_dist))
                   2098:            {
1.1.1.2   christos 2099:              best_dist = (bfd_vma) min_dist;
1.1       christos 2100:              best_fdr = fdr_ptr;
                   2101:              best_pdr = pdr_hold;
                   2102:            }
                   2103:          /* Continue looping until base_addr of next entry is different.  */
                   2104:        }
                   2105:       /* eraxxon: We want to iterate over all FDRs.
                   2106:         See previous comment about 'fdrtab_lookup'.  */
                   2107:       while (++i < line_info->fdrtab_len);
                   2108:
                   2109:       if (!best_fdr || !best_pdr)
                   2110:        return FALSE;                   /* Shouldn't happen...  */
                   2111:
                   2112:       /* Phew, finally we got something that we can hold onto.  */
                   2113:       fdr_ptr = best_fdr;
                   2114:       pdr_ptr = best_pdr;
                   2115:       (*debug_swap->swap_pdr_in) (abfd, pdr_ptr, &pdr);
                   2116:       /* Now we can look for the actual line number.  The line numbers
                   2117:          are stored in a very funky format, which I won't try to
                   2118:          describe.  The search is bounded by the end of the FDRs line
                   2119:          number entries.  */
                   2120:       line_end = debug_info->line + fdr_ptr->cbLineOffset + fdr_ptr->cbLine;
                   2121:
                   2122:       /* Make offset relative to procedure entry.  */
                   2123:       offset -= pdr.adr - 0x10 * pdr.prof;
                   2124:       lineno = pdr.lnLow;
                   2125:       line_ptr = debug_info->line + fdr_ptr->cbLineOffset + pdr.cbLineOffset;
                   2126:       while (line_ptr < line_end)
                   2127:        {
                   2128:          int delta;
                   2129:          unsigned int count;
                   2130:
                   2131:          delta = *line_ptr >> 4;
                   2132:          if (delta >= 0x8)
                   2133:            delta -= 0x10;
                   2134:          count = (*line_ptr & 0xf) + 1;
                   2135:          ++line_ptr;
                   2136:          if (delta == -8)
                   2137:            {
                   2138:              delta = (((line_ptr[0]) & 0xff) << 8) + ((line_ptr[1]) & 0xff);
                   2139:              if (delta >= 0x8000)
                   2140:                delta -= 0x10000;
                   2141:              line_ptr += 2;
                   2142:            }
                   2143:          lineno += delta;
                   2144:          if (offset < count * 4)
                   2145:            {
                   2146:              line_info->cache.stop += count * 4 - offset;
                   2147:              break;
                   2148:            }
                   2149:          offset -= count * 4;
                   2150:        }
                   2151:
                   2152:       /* If fdr_ptr->rss is -1, then this file does not have full
                   2153:          symbols, at least according to gdb/mipsread.c.  */
                   2154:       if (fdr_ptr->rss == -1)
                   2155:        {
                   2156:          line_info->cache.filename = NULL;
                   2157:          if (pdr.isym == -1)
                   2158:            line_info->cache.functionname = NULL;
                   2159:          else
                   2160:            {
                   2161:              EXTR proc_ext;
                   2162:
                   2163:              (*debug_swap->swap_ext_in)
                   2164:                (abfd,
                   2165:                 ((char *) debug_info->external_ext
                   2166:                  + pdr.isym * debug_swap->external_ext_size),
                   2167:                 &proc_ext);
                   2168:              line_info->cache.functionname = (debug_info->ssext
                   2169:                                               + proc_ext.asym.iss);
                   2170:            }
                   2171:        }
                   2172:       else
                   2173:        {
                   2174:          SYMR proc_sym;
                   2175:
                   2176:          line_info->cache.filename = (debug_info->ss
                   2177:                                       + fdr_ptr->issBase
                   2178:                                       + fdr_ptr->rss);
                   2179:          (*debug_swap->swap_sym_in)
                   2180:            (abfd,
                   2181:             ((char *) debug_info->external_sym
                   2182:              + ((fdr_ptr->isymBase + pdr.isym)
                   2183:                 * debug_swap->external_sym_size)),
                   2184:             &proc_sym);
                   2185:          line_info->cache.functionname = (debug_info->ss
                   2186:                                           + fdr_ptr->issBase
                   2187:                                           + proc_sym.iss);
                   2188:        }
                   2189:       if (lineno == ilineNil)
                   2190:        lineno = 0;
                   2191:       line_info->cache.line_num = lineno;
                   2192:     }
                   2193:   else
                   2194:     {
                   2195:       bfd_size_type external_sym_size;
                   2196:       const char *directory_name;
                   2197:       const char *main_file_name;
                   2198:       const char *current_file_name;
                   2199:       const char *function_name;
                   2200:       const char *line_file_name;
                   2201:       bfd_vma low_func_vma;
                   2202:       bfd_vma low_line_vma;
                   2203:       bfd_boolean past_line;
                   2204:       bfd_boolean past_fn;
                   2205:       char *sym_ptr, *sym_ptr_end;
                   2206:       size_t len, funclen;
                   2207:       char *buffer = NULL;
                   2208:
                   2209:       /* This file uses stabs debugging information.  When gcc is not
                   2210:         optimizing, it will put the line number information before
                   2211:         the function name stabs entry.  When gcc is optimizing, it
                   2212:         will put the stabs entry for all the function first, followed
                   2213:         by the line number information.  (This appears to happen
                   2214:         because of the two output files used by the -mgpopt switch,
                   2215:         which is implied by -O).  This means that we must keep
                   2216:         looking through the symbols until we find both a line number
                   2217:         and a function name which are beyond the address we want.  */
                   2218:
                   2219:       line_info->cache.filename = NULL;
                   2220:       line_info->cache.functionname = NULL;
                   2221:       line_info->cache.line_num = 0;
                   2222:
                   2223:       directory_name = NULL;
                   2224:       main_file_name = NULL;
                   2225:       current_file_name = NULL;
                   2226:       function_name = NULL;
                   2227:       line_file_name = NULL;
                   2228:       low_func_vma = 0;
                   2229:       low_line_vma = 0;
                   2230:       past_line = FALSE;
                   2231:       past_fn = FALSE;
                   2232:
                   2233:       external_sym_size = debug_swap->external_sym_size;
                   2234:
                   2235:       sym_ptr = ((char *) debug_info->external_sym
                   2236:                 + (fdr_ptr->isymBase + 2) * external_sym_size);
                   2237:       sym_ptr_end = sym_ptr + (fdr_ptr->csym - 2) * external_sym_size;
                   2238:       for (;
                   2239:           sym_ptr < sym_ptr_end && (! past_line || ! past_fn);
                   2240:           sym_ptr += external_sym_size)
                   2241:        {
                   2242:          SYMR sym;
                   2243:
                   2244:          (*debug_swap->swap_sym_in) (abfd, sym_ptr, &sym);
                   2245:
                   2246:          if (ECOFF_IS_STAB (&sym))
                   2247:            {
                   2248:              switch (ECOFF_UNMARK_STAB (sym.index))
                   2249:                {
                   2250:                case N_SO:
                   2251:                  main_file_name = current_file_name =
                   2252:                    debug_info->ss + fdr_ptr->issBase + sym.iss;
                   2253:
                   2254:                  /* Check the next symbol to see if it is also an
                   2255:                      N_SO symbol.  */
                   2256:                  if (sym_ptr + external_sym_size < sym_ptr_end)
                   2257:                    {
                   2258:                      SYMR nextsym;
                   2259:
                   2260:                      (*debug_swap->swap_sym_in) (abfd,
                   2261:                                                  sym_ptr + external_sym_size,
                   2262:                                                  &nextsym);
                   2263:                      if (ECOFF_IS_STAB (&nextsym)
                   2264:                          && ECOFF_UNMARK_STAB (nextsym.index) == N_SO)
                   2265:                        {
                   2266:                          directory_name = current_file_name;
                   2267:                          main_file_name = current_file_name =
                   2268:                            debug_info->ss + fdr_ptr->issBase + nextsym.iss;
                   2269:                          sym_ptr += external_sym_size;
                   2270:                        }
                   2271:                    }
                   2272:                  break;
                   2273:
                   2274:                case N_SOL:
                   2275:                  current_file_name =
                   2276:                    debug_info->ss + fdr_ptr->issBase + sym.iss;
                   2277:                  break;
                   2278:
                   2279:                case N_FUN:
                   2280:                  if (sym.value > offset)
                   2281:                    past_fn = TRUE;
                   2282:                  else if (sym.value >= low_func_vma)
                   2283:                    {
                   2284:                      low_func_vma = sym.value;
                   2285:                      function_name =
                   2286:                        debug_info->ss + fdr_ptr->issBase + sym.iss;
                   2287:                    }
                   2288:                  break;
                   2289:                }
                   2290:            }
                   2291:          else if (sym.st == stLabel && sym.index != indexNil)
                   2292:            {
                   2293:              if (sym.value > offset)
                   2294:                past_line = TRUE;
                   2295:              else if (sym.value >= low_line_vma)
                   2296:                {
                   2297:                  low_line_vma = sym.value;
                   2298:                  line_file_name = current_file_name;
                   2299:                  line_info->cache.line_num = sym.index;
                   2300:                }
                   2301:            }
                   2302:        }
                   2303:
                   2304:       if (line_info->cache.line_num != 0)
                   2305:        main_file_name = line_file_name;
                   2306:
                   2307:       /* We need to remove the stuff after the colon in the function
                   2308:          name.  We also need to put the directory name and the file
                   2309:          name together.  */
                   2310:       if (function_name == NULL)
                   2311:        len = funclen = 0;
                   2312:       else
                   2313:        len = funclen = strlen (function_name) + 1;
                   2314:
                   2315:       if (main_file_name != NULL
                   2316:          && directory_name != NULL
                   2317:          && main_file_name[0] != '/')
                   2318:        len += strlen (directory_name) + strlen (main_file_name) + 1;
                   2319:
                   2320:       if (len != 0)
                   2321:        {
                   2322:          if (line_info->find_buffer != NULL)
                   2323:            free (line_info->find_buffer);
                   2324:          buffer = (char *) bfd_malloc ((bfd_size_type) len);
                   2325:          if (buffer == NULL)
                   2326:            return FALSE;
                   2327:          line_info->find_buffer = buffer;
                   2328:        }
                   2329:
                   2330:       if (function_name != NULL)
                   2331:        {
                   2332:          char *colon;
                   2333:
                   2334:          strcpy (buffer, function_name);
                   2335:          colon = strchr (buffer, ':');
                   2336:          if (colon != NULL)
                   2337:            *colon = '\0';
                   2338:          line_info->cache.functionname = buffer;
                   2339:        }
                   2340:
                   2341:       if (main_file_name != NULL)
                   2342:        {
                   2343:          if (directory_name == NULL || main_file_name[0] == '/')
                   2344:            line_info->cache.filename = main_file_name;
                   2345:          else
                   2346:            {
                   2347:              sprintf (buffer + funclen, "%s%s", directory_name,
                   2348:                       main_file_name);
                   2349:              line_info->cache.filename = buffer + funclen;
                   2350:            }
                   2351:        }
                   2352:     }
                   2353:
                   2354:   return TRUE;
                   2355: }
                   2356:
                   2357: /* Do the work of find_nearest_line.  */
                   2358:
                   2359: bfd_boolean
                   2360: _bfd_ecoff_locate_line (bfd *abfd,
                   2361:                        asection *section,
                   2362:                        bfd_vma offset,
                   2363:                        struct ecoff_debug_info * const debug_info,
                   2364:                        const struct ecoff_debug_swap * const debug_swap,
                   2365:                        struct ecoff_find_line *line_info,
                   2366:                        const char **filename_ptr,
                   2367:                        const char **functionname_ptr,
                   2368:                        unsigned int *retline_ptr)
                   2369: {
                   2370:   offset += section->vma;
                   2371:
                   2372:   if (line_info->cache.sect == NULL
                   2373:       || line_info->cache.sect != section
                   2374:       || offset < line_info->cache.start
                   2375:       || offset >= line_info->cache.stop)
                   2376:     {
                   2377:       line_info->cache.sect = section;
                   2378:       line_info->cache.start = offset;
                   2379:       line_info->cache.stop = offset;
                   2380:       if (! lookup_line (abfd, debug_info, debug_swap, line_info))
                   2381:        {
                   2382:          line_info->cache.sect = NULL;
                   2383:          return FALSE;
                   2384:        }
                   2385:     }
                   2386:
                   2387:   *filename_ptr = line_info->cache.filename;
                   2388:   *functionname_ptr = line_info->cache.functionname;
                   2389:   *retline_ptr = line_info->cache.line_num;
                   2390:
                   2391:   return TRUE;
                   2392: }
                   2393: 
                   2394: /* These routines copy symbolic information into a memory buffer.
                   2395:
                   2396:    FIXME: The whole point of the shuffle code is to avoid storing
                   2397:    everything in memory, since the linker is such a memory hog.  This
                   2398:    code makes that effort useless.  It is only called by the MIPS ELF
                   2399:    code when generating a shared library, so it is not that big a
                   2400:    deal, but it should be fixed eventually.  */
                   2401:
                   2402: /* Collect a shuffle into a memory buffer.  */
                   2403:
                   2404: static bfd_boolean
                   2405: ecoff_collect_shuffle (struct shuffle *l, bfd_byte *buff)
                   2406: {
                   2407:   unsigned long total;
                   2408:
                   2409:   total = 0;
                   2410:   for (; l != (struct shuffle *) NULL; l = l->next)
                   2411:     {
                   2412:       if (! l->filep)
                   2413:        memcpy (buff, l->u.memory, l->size);
                   2414:       else
                   2415:        {
                   2416:          if (bfd_seek (l->u.file.input_bfd, l->u.file.offset, SEEK_SET) != 0
                   2417:              || (bfd_bread (buff, (bfd_size_type) l->size, l->u.file.input_bfd)
                   2418:                  != l->size))
                   2419:            return FALSE;
                   2420:        }
                   2421:       total += l->size;
                   2422:       buff += l->size;
                   2423:     }
                   2424:
                   2425:   return TRUE;
                   2426: }
                   2427:
                   2428: /* Copy PDR information into a memory buffer.  */
                   2429:
                   2430: bfd_boolean
                   2431: _bfd_ecoff_get_accumulated_pdr (void * handle,
                   2432:                                bfd_byte *buff)
                   2433: {
                   2434:   struct accumulate *ainfo = (struct accumulate *) handle;
                   2435:
                   2436:   return ecoff_collect_shuffle (ainfo->pdr, buff);
                   2437: }
                   2438:
                   2439: /* Copy symbol information into a memory buffer.  */
                   2440:
                   2441: bfd_boolean
                   2442: _bfd_ecoff_get_accumulated_sym (void * handle, bfd_byte *buff)
                   2443: {
                   2444:   struct accumulate *ainfo = (struct accumulate *) handle;
                   2445:
                   2446:   return ecoff_collect_shuffle (ainfo->sym, buff);
                   2447: }
                   2448:
                   2449: /* Copy the string table into a memory buffer.  */
                   2450:
                   2451: bfd_boolean
                   2452: _bfd_ecoff_get_accumulated_ss (void * handle, bfd_byte *buff)
                   2453: {
                   2454:   struct accumulate *ainfo = (struct accumulate *) handle;
                   2455:   struct string_hash_entry *sh;
                   2456:   unsigned long total;
                   2457:
                   2458:   /* The string table is written out from the hash table if this is a
                   2459:      final link.  */
                   2460:   BFD_ASSERT (ainfo->ss == (struct shuffle *) NULL);
                   2461:   *buff++ = '\0';
                   2462:   total = 1;
                   2463:   BFD_ASSERT (ainfo->ss_hash == NULL || ainfo->ss_hash->val == 1);
                   2464:   for (sh = ainfo->ss_hash;
                   2465:        sh != (struct string_hash_entry *) NULL;
                   2466:        sh = sh->next)
                   2467:     {
                   2468:       size_t len;
                   2469:
                   2470:       len = strlen (sh->root.string);
                   2471:       memcpy (buff, sh->root.string, len + 1);
                   2472:       total += len + 1;
                   2473:       buff += len + 1;
                   2474:     }
                   2475:
                   2476:   return TRUE;
                   2477: }

CVSweb <webmaster@jp.NetBSD.org>