OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [trunk/] [insight/] [bfd/] [ecofflink.c] - Blame information for rev 1765

Details | Compare with Previous | View Log

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

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.