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

Subversion Repositories scarts

[/] [scarts/] [trunk/] [toolchain/] [scarts-binutils/] [binutils-2.19.1/] [gprof/] [corefile.c] - Blame information for rev 6

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 6 jlechner
/* corefile.c
2
 
3
   Copyright 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2007, 2008
4
   Free Software Foundation, Inc.
5
 
6
   This file is part of GNU Binutils.
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 3 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., 51 Franklin Street - Fifth Floor, Boston, MA
21
   02110-1301, USA.  */
22
 
23
#include "gprof.h"
24
#include "libiberty.h"
25
#include "search_list.h"
26
#include "source.h"
27
#include "symtab.h"
28
#include "hist.h"
29
#include "corefile.h"
30
#include "safe-ctype.h"
31
 
32
bfd *core_bfd;
33
static int core_num_syms;
34
static asymbol **core_syms;
35
asection *core_text_sect;
36
PTR core_text_space;
37
 
38
static int min_insn_size;
39
int offset_to_code;
40
 
41
/* For mapping symbols to specific .o files during file ordering.  */
42
struct function_map *symbol_map;
43
unsigned int symbol_map_count;
44
 
45
static void read_function_mappings (const char *);
46
static int core_sym_class (asymbol *);
47
static bfd_boolean get_src_info
48
  (bfd_vma, const char **, const char **, int *);
49
 
50
extern void i386_find_call  (Sym *, bfd_vma, bfd_vma);
51
extern void alpha_find_call (Sym *, bfd_vma, bfd_vma);
52
extern void vax_find_call   (Sym *, bfd_vma, bfd_vma);
53
extern void tahoe_find_call (Sym *, bfd_vma, bfd_vma);
54
extern void sparc_find_call (Sym *, bfd_vma, bfd_vma);
55
extern void mips_find_call  (Sym *, bfd_vma, bfd_vma);
56
 
57
static void
58
parse_error (const char *filename)
59
{
60
  fprintf (stderr, _("%s: unable to parse mapping file %s.\n"), whoami, filename);
61
  done (1);
62
}
63
 
64
static void
65
read_function_mappings (const char *filename)
66
{
67
  FILE *file = fopen (filename, "r");
68
  char dummy[1024];
69
  int count = 0;
70
 
71
  if (!file)
72
    {
73
      fprintf (stderr, _("%s: could not open %s.\n"), whoami, filename);
74
      done (1);
75
    }
76
 
77
  /* First parse the mapping file so we know how big we need to
78
     make our tables.  We also do some sanity checks at this
79
     time.  */
80
  while (!feof (file))
81
    {
82
      int matches;
83
 
84
      matches = fscanf (file, "%[^\n:]", dummy);
85
      if (!matches)
86
        parse_error (filename);
87
 
88
      /* Just skip messages about files with no symbols.  */
89
      if (!strncmp (dummy, "No symbols in ", 14))
90
        {
91
          matches = fscanf (file, "\n");
92
          if (matches == EOF)
93
            parse_error (filename);
94
          continue;
95
        }
96
 
97
      /* Don't care what else is on this line at this point.  */
98
      matches = fscanf (file, "%[^\n]\n", dummy);
99
      if (!matches)
100
        parse_error (filename);
101
      count++;
102
    }
103
 
104
  /* Now we know how big we need to make our table.  */
105
  symbol_map = ((struct function_map *)
106
                xmalloc (count * sizeof (struct function_map)));
107
 
108
  /* Rewind the input file so we can read it again.  */
109
  rewind (file);
110
 
111
  /* Read each entry and put it into the table.  */
112
  count = 0;
113
  while (!feof (file))
114
    {
115
      int matches;
116
      char *tmp;
117
 
118
      matches = fscanf (file, "%[^\n:]", dummy);
119
      if (!matches)
120
        parse_error (filename);
121
 
122
      /* Just skip messages about files with no symbols.  */
123
      if (!strncmp (dummy, "No symbols in ", 14))
124
        {
125
          matches = fscanf (file, "\n");
126
          if (matches == EOF)
127
            parse_error (filename);
128
          continue;
129
        }
130
 
131
      /* dummy has the filename, go ahead and copy it.  */
132
      symbol_map[count].file_name = xmalloc (strlen (dummy) + 1);
133
      strcpy (symbol_map[count].file_name, dummy);
134
 
135
      /* Now we need the function name.  */
136
      matches = fscanf (file, "%[^\n]\n", dummy);
137
      if (!matches)
138
        parse_error (filename);
139
      tmp = strrchr (dummy, ' ') + 1;
140
      symbol_map[count].function_name = xmalloc (strlen (tmp) + 1);
141
      strcpy (symbol_map[count].function_name, tmp);
142
      count++;
143
    }
144
 
145
  /* Record the size of the map table for future reference.  */
146
  symbol_map_count = count;
147
}
148
 
149
 
150
void
151
core_init (const char *aout_name)
152
{
153
  int core_sym_bytes;
154
  asymbol *synthsyms;
155
  long synth_count;
156
 
157
  core_bfd = bfd_openr (aout_name, 0);
158
 
159
  if (!core_bfd)
160
    {
161
      perror (aout_name);
162
      done (1);
163
    }
164
 
165
  if (!bfd_check_format (core_bfd, bfd_object))
166
    {
167
      fprintf (stderr, _("%s: %s: not in executable format\n"), whoami, aout_name);
168
      done (1);
169
    }
170
 
171
  /* Get core's text section.  */
172
  core_text_sect = bfd_get_section_by_name (core_bfd, ".text");
173
  if (!core_text_sect)
174
    {
175
      core_text_sect = bfd_get_section_by_name (core_bfd, "$CODE$");
176
      if (!core_text_sect)
177
        {
178
          fprintf (stderr, _("%s: can't find .text section in %s\n"),
179
                   whoami, aout_name);
180
          done (1);
181
        }
182
    }
183
 
184
  /* Read core's symbol table.  */
185
 
186
  /* This will probably give us more than we need, but that's ok.  */
187
  core_sym_bytes = bfd_get_symtab_upper_bound (core_bfd);
188
  if (core_sym_bytes < 0)
189
    {
190
      fprintf (stderr, "%s: %s: %s\n", whoami, aout_name,
191
               bfd_errmsg (bfd_get_error ()));
192
      done (1);
193
    }
194
 
195
  core_syms = (asymbol **) xmalloc (core_sym_bytes);
196
  core_num_syms = bfd_canonicalize_symtab (core_bfd, core_syms);
197
 
198
  if (core_num_syms < 0)
199
    {
200
      fprintf (stderr, "%s: %s: %s\n", whoami, aout_name,
201
               bfd_errmsg (bfd_get_error ()));
202
      done (1);
203
    }
204
 
205
  synth_count = bfd_get_synthetic_symtab (core_bfd, core_num_syms, core_syms,
206
                                          0, NULL, &synthsyms);
207
  if (synth_count > 0)
208
    {
209
      asymbol **symp;
210
      long new_size;
211
      long i;
212
 
213
      new_size = (core_num_syms + synth_count + 1) * sizeof (*core_syms);
214
      core_syms = xrealloc (core_syms, new_size);
215
      symp = core_syms + core_num_syms;
216
      core_num_syms += synth_count;
217
      for (i = 0; i < synth_count; i++)
218
        *symp++ = synthsyms + i;
219
      *symp = 0;
220
    }
221
 
222
  min_insn_size = 1;
223
  offset_to_code = 0;
224
 
225
  switch (bfd_get_arch (core_bfd))
226
    {
227
    case bfd_arch_vax:
228
    case bfd_arch_tahoe:
229
      offset_to_code = 2;
230
      break;
231
 
232
    case bfd_arch_alpha:
233
      min_insn_size = 4;
234
      break;
235
 
236
    default:
237
      break;
238
    }
239
 
240
  if (function_mapping_file)
241
    read_function_mappings (function_mapping_file);
242
}
243
 
244
/* Read in the text space of an a.out file.  */
245
 
246
void
247
core_get_text_space (bfd *cbfd)
248
{
249
  core_text_space = malloc (bfd_get_section_size (core_text_sect));
250
 
251
  if (!core_text_space)
252
    {
253
      fprintf (stderr, _("%s: ran out room for %lu bytes of text space\n"),
254
               whoami, (unsigned long) bfd_get_section_size (core_text_sect));
255
      done (1);
256
    }
257
 
258
  if (!bfd_get_section_contents (cbfd, core_text_sect, core_text_space,
259
                                 0, bfd_get_section_size (core_text_sect)))
260
    {
261
      bfd_perror ("bfd_get_section_contents");
262
      free (core_text_space);
263
      core_text_space = 0;
264
    }
265
 
266
  if (!core_text_space)
267
    fprintf (stderr, _("%s: can't do -c\n"), whoami);
268
}
269
 
270
 
271
void
272
find_call (Sym *parent, bfd_vma p_lowpc, bfd_vma p_highpc)
273
{
274
  if (core_text_space == 0)
275
    return;
276
 
277
  hist_clip_symbol_address (&p_lowpc, &p_highpc);
278
 
279
  switch (bfd_get_arch (core_bfd))
280
    {
281
    case bfd_arch_i386:
282
      i386_find_call (parent, p_lowpc, p_highpc);
283
      break;
284
 
285
    case bfd_arch_alpha:
286
      alpha_find_call (parent, p_lowpc, p_highpc);
287
      break;
288
 
289
    case bfd_arch_vax:
290
      vax_find_call (parent, p_lowpc, p_highpc);
291
      break;
292
 
293
    case bfd_arch_sparc:
294
      sparc_find_call (parent, p_lowpc, p_highpc);
295
      break;
296
 
297
    case bfd_arch_tahoe:
298
      tahoe_find_call (parent, p_lowpc, p_highpc);
299
      break;
300
 
301
    case bfd_arch_mips:
302
      mips_find_call (parent, p_lowpc, p_highpc);
303
      break;
304
 
305
    default:
306
      fprintf (stderr, _("%s: -c not supported on architecture %s\n"),
307
               whoami, bfd_printable_name(core_bfd));
308
 
309
      /* Don't give the error more than once.  */
310
      ignore_direct_calls = FALSE;
311
    }
312
}
313
 
314
/* Return class of symbol SYM.  The returned class can be any of:
315
 
316
        'T' -> symbol is a global name
317
        't' -> symbol is a local (static) name.  */
318
 
319
static int
320
core_sym_class (asymbol *sym)
321
{
322
  symbol_info syminfo;
323
  const char *name;
324
  char sym_prefix;
325
  int i;
326
 
327
  if (sym->section == NULL || (sym->flags & BSF_DEBUGGING) != 0)
328
    return 0;
329
 
330
  /* Must be a text symbol, and static text symbols
331
     don't qualify if ignore_static_funcs set.   */
332
  if (ignore_static_funcs && (sym->flags & BSF_LOCAL))
333
    {
334
      DBG (AOUTDEBUG, printf ("[core_sym_class] %s: not a function\n",
335
                              sym->name));
336
      return 0;
337
    }
338
 
339
  bfd_get_symbol_info (core_bfd, sym, &syminfo);
340
  i = syminfo.type;
341
 
342
  if (i == 'T')
343
    return i;                   /* It's a global symbol.  */
344
 
345
  if (i == 'W')
346
    /* Treat weak symbols as text symbols.  FIXME: a weak symbol may
347
       also be a data symbol.  */
348
    return 'T';
349
 
350
  if (i != 't')
351
    {
352
      /* Not a static text symbol.  */
353
      DBG (AOUTDEBUG, printf ("[core_sym_class] %s is of class %c\n",
354
                              sym->name, i));
355
      return 0;
356
    }
357
 
358
  /* Do some more filtering on static function-names.  */
359
  if (ignore_static_funcs)
360
    return 0;
361
 
362
  /* Can't zero-length name or funny characters in name, where
363
     `funny' includes: `.' (.o file names) and `$' (Pascal labels).  */
364
  if (!sym->name || sym->name[0] == '\0')
365
    return 0;
366
 
367
  for (name = sym->name; *name; ++name)
368
    {
369
      if (*name == '$')
370
        return 0;
371
 
372
      /* Do not discard nested subprograms (those
373
         which end with .NNN, where N are digits).  */
374
      if (*name == '.')
375
        for (name++; *name; name++)
376
          if (! ISDIGIT (*name))
377
            return 0;
378
    }
379
 
380
  /* On systems where the C compiler adds an underscore to all
381
     names, static names without underscores seem usually to be
382
     labels in hand written assembler in the library.  We don't want
383
     these names.  This is certainly necessary on a Sparc running
384
     SunOS 4.1 (try profiling a program that does a lot of
385
     division). I don't know whether it has harmful side effects on
386
     other systems.  Perhaps it should be made configurable.  */
387
  sym_prefix = bfd_get_symbol_leading_char (core_bfd);
388
 
389
  if ((sym_prefix && sym_prefix != sym->name[0])
390
      /* GCC may add special symbols to help gdb figure out the file
391
        language.  We want to ignore these, since sometimes they mask
392
        the real function.  (dj@ctron)  */
393
      || !strncmp (sym->name, "__gnu_compiled", 14)
394
      || !strncmp (sym->name, "___gnu_compiled", 15))
395
    {
396
      return 0;
397
    }
398
 
399
  /* If the object file supports marking of function symbols, then
400
     we can zap anything that doesn't have BSF_FUNCTION set.  */
401
  if (ignore_non_functions && (sym->flags & BSF_FUNCTION) == 0)
402
    return 0;
403
 
404
  return 't';                   /* It's a static text symbol.  */
405
}
406
 
407
/* Get whatever source info we can get regarding address ADDR.  */
408
 
409
static bfd_boolean
410
get_src_info (bfd_vma addr, const char **filename, const char **name, int *line_num)
411
{
412
  const char *fname = 0, *func_name = 0;
413
  int l = 0;
414
 
415
  if (bfd_find_nearest_line (core_bfd, core_text_sect, core_syms,
416
                             addr - core_text_sect->vma,
417
                             &fname, &func_name, (unsigned int *) &l)
418
      && fname && func_name && l)
419
    {
420
      DBG (AOUTDEBUG, printf ("[get_src_info] 0x%lx -> %s:%d (%s)\n",
421
                              (unsigned long) addr, fname, l, func_name));
422
      *filename = fname;
423
      *name = func_name;
424
      *line_num = l;
425
      return TRUE;
426
    }
427
  else
428
    {
429
      DBG (AOUTDEBUG, printf ("[get_src_info] no info for 0x%lx (%s:%d,%s)\n",
430
                              (unsigned long) addr,
431
                              fname ? fname : "<unknown>", l,
432
                              func_name ? func_name : "<unknown>"));
433
      return FALSE;
434
    }
435
}
436
 
437
/* Read in symbol table from core.
438
   One symbol per function is entered.  */
439
 
440
void
441
core_create_function_syms ()
442
{
443
  bfd_vma min_vma = ~(bfd_vma) 0;
444
  bfd_vma max_vma = 0;
445
  int class;
446
  long i, found, skip;
447
  unsigned int j;
448
 
449
  /* Pass 1 - determine upper bound on number of function names.  */
450
  symtab.len = 0;
451
 
452
  for (i = 0; i < core_num_syms; ++i)
453
    {
454
      if (!core_sym_class (core_syms[i]))
455
        continue;
456
 
457
      /* This should be replaced with a binary search or hashed
458
         search.  Gross.
459
 
460
         Don't create a symtab entry for a function that has
461
         a mapping to a file, unless it's the first function
462
         in the file.  */
463
      skip = 0;
464
      for (j = 0; j < symbol_map_count; j++)
465
        if (!strcmp (core_syms[i]->name, symbol_map[j].function_name))
466
          {
467
            if (j > 0 && ! strcmp (symbol_map [j].file_name,
468
                                   symbol_map [j - 1].file_name))
469
              skip = 1;
470
            break;
471
          }
472
 
473
      if (!skip)
474
        ++symtab.len;
475
    }
476
 
477
  if (symtab.len == 0)
478
    {
479
      fprintf (stderr, _("%s: file `%s' has no symbols\n"), whoami, a_out_name);
480
      done (1);
481
    }
482
 
483
  /* The "+ 2" is for the sentinels.  */
484
  symtab.base = (Sym *) xmalloc ((symtab.len + 2) * sizeof (Sym));
485
 
486
  /* Pass 2 - create symbols.  */
487
  symtab.limit = symtab.base;
488
 
489
  for (i = 0; i < core_num_syms; ++i)
490
    {
491
      asection *sym_sec;
492
 
493
      class = core_sym_class (core_syms[i]);
494
 
495
      if (!class)
496
        {
497
          DBG (AOUTDEBUG,
498
               printf ("[core_create_function_syms] rejecting: 0x%lx %s\n",
499
                       (unsigned long) core_syms[i]->value,
500
                       core_syms[i]->name));
501
          continue;
502
        }
503
 
504
      /* This should be replaced with a binary search or hashed
505
         search.  Gross.   */
506
      skip = 0;
507
      found = 0;
508
 
509
      for (j = 0; j < symbol_map_count; j++)
510
        if (!strcmp (core_syms[i]->name, symbol_map[j].function_name))
511
          {
512
            if (j > 0 && ! strcmp (symbol_map [j].file_name,
513
                                   symbol_map [j - 1].file_name))
514
              skip = 1;
515
            else
516
              found = j;
517
            break;
518
          }
519
 
520
      if (skip)
521
        continue;
522
 
523
      sym_init (symtab.limit);
524
 
525
      /* Symbol offsets are always section-relative.  */
526
      sym_sec = core_syms[i]->section;
527
      symtab.limit->addr = core_syms[i]->value;
528
      if (sym_sec)
529
        symtab.limit->addr += bfd_get_section_vma (sym_sec->owner, sym_sec);
530
 
531
      if (symbol_map_count
532
          && !strcmp (core_syms[i]->name, symbol_map[found].function_name))
533
        {
534
          symtab.limit->name = symbol_map[found].file_name;
535
          symtab.limit->mapped = 1;
536
        }
537
      else
538
        {
539
          symtab.limit->name = core_syms[i]->name;
540
          symtab.limit->mapped = 0;
541
        }
542
 
543
      /* Lookup filename and line number, if we can.  */
544
      {
545
        const char *filename, *func_name;
546
 
547
        if (get_src_info (symtab.limit->addr, &filename, &func_name,
548
                          &symtab.limit->line_num))
549
          {
550
            symtab.limit->file = source_file_lookup_path (filename);
551
 
552
            /* FIXME: Checking __osf__ here does not work with a cross
553
               gprof.  */
554
#ifdef __osf__
555
            /* Suppress symbols that are not function names.  This is
556
               useful to suppress code-labels and aliases.
557
 
558
               This is known to be useful under DEC's OSF/1.  Under SunOS 4.x,
559
               labels do not appear in the symbol table info, so this isn't
560
               necessary.  */
561
 
562
            if (strcmp (symtab.limit->name, func_name) != 0)
563
              {
564
                /* The symbol's address maps to a different name, so
565
                   it can't be a function-entry point.  This happens
566
                   for labels, for example.  */
567
                DBG (AOUTDEBUG,
568
                     printf ("[core_create_function_syms: rej %s (maps to %s)\n",
569
                             symtab.limit->name, func_name));
570
                continue;
571
              }
572
#endif
573
          }
574
      }
575
 
576
      symtab.limit->is_func = TRUE;
577
      symtab.limit->is_bb_head = TRUE;
578
 
579
      if (class == 't')
580
        symtab.limit->is_static = TRUE;
581
 
582
      /* Keep track of the minimum and maximum vma addresses used by all
583
         symbols.  When computing the max_vma, use the ending address of the
584
         section containing the symbol, if available.  */
585
      min_vma = MIN (symtab.limit->addr, min_vma);
586
      if (sym_sec)
587
        max_vma = MAX (bfd_get_section_vma (sym_sec->owner, sym_sec)
588
                       + bfd_section_size (sym_sec->owner, sym_sec) - 1,
589
                       max_vma);
590
      else
591
        max_vma = MAX (symtab.limit->addr, max_vma);
592
 
593
      DBG (AOUTDEBUG, printf ("[core_create_function_syms] %ld %s 0x%lx\n",
594
                              (long) (symtab.limit - symtab.base),
595
                              symtab.limit->name,
596
                              (unsigned long) symtab.limit->addr));
597
      ++symtab.limit;
598
    }
599
 
600
  /* Create sentinels.  */
601
  sym_init (symtab.limit);
602
  symtab.limit->name = "<locore>";
603
  symtab.limit->addr = 0;
604
  symtab.limit->end_addr = min_vma - 1;
605
  ++symtab.limit;
606
 
607
  sym_init (symtab.limit);
608
  symtab.limit->name = "<hicore>";
609
  symtab.limit->addr = max_vma + 1;
610
  symtab.limit->end_addr = ~(bfd_vma) 0;
611
  ++symtab.limit;
612
 
613
  symtab.len = symtab.limit - symtab.base;
614
  symtab_finalize (&symtab);
615
}
616
 
617
/* Read in symbol table from core.
618
   One symbol per line of source code is entered.  */
619
 
620
void
621
core_create_line_syms ()
622
{
623
  char *prev_name, *prev_filename;
624
  unsigned int prev_name_len, prev_filename_len;
625
  bfd_vma vma, min_vma = ~(bfd_vma) 0, max_vma = 0;
626
  Sym *prev, dummy, *sentinel, *sym;
627
  const char *filename;
628
  int prev_line_num;
629
  Sym_Table ltab;
630
  bfd_vma vma_high;
631
 
632
  /* Create symbols for functions as usual.  This is necessary in
633
     cases where parts of a program were not compiled with -g.  For
634
     those parts we still want to get info at the function level.  */
635
  core_create_function_syms ();
636
 
637
  /* Pass 1: count the number of symbols.  */
638
 
639
  /* To find all line information, walk through all possible
640
     text-space addresses (one by one!) and get the debugging
641
     info for each address.  When the debugging info changes,
642
     it is time to create a new symbol.
643
 
644
     Of course, this is rather slow and it would be better if
645
     BFD would provide an iterator for enumerating all line infos.  */
646
  prev_name_len = PATH_MAX;
647
  prev_filename_len = PATH_MAX;
648
  prev_name = xmalloc (prev_name_len);
649
  prev_filename = xmalloc (prev_filename_len);
650
  ltab.len = 0;
651
  prev_line_num = 0;
652
 
653
  vma_high = core_text_sect->vma + bfd_get_section_size (core_text_sect);
654
  for (vma = core_text_sect->vma; vma < vma_high; vma += min_insn_size)
655
    {
656
      unsigned int len;
657
 
658
      if (!get_src_info (vma, &filename, &dummy.name, &dummy.line_num)
659
          || (prev_line_num == dummy.line_num
660
              && prev_name != NULL
661
              && strcmp (prev_name, dummy.name) == 0
662
              && strcmp (prev_filename, filename) == 0))
663
        continue;
664
 
665
      ++ltab.len;
666
      prev_line_num = dummy.line_num;
667
 
668
      len = strlen (dummy.name);
669
      if (len >= prev_name_len)
670
        {
671
          prev_name_len = len + 1024;
672
          free (prev_name);
673
          prev_name = xmalloc (prev_name_len);
674
        }
675
 
676
      strcpy (prev_name, dummy.name);
677
      len = strlen (filename);
678
 
679
      if (len >= prev_filename_len)
680
        {
681
          prev_filename_len = len + 1024;
682
          free (prev_filename);
683
          prev_filename = xmalloc (prev_filename_len);
684
        }
685
 
686
      strcpy (prev_filename, filename);
687
 
688
      min_vma = MIN (vma, min_vma);
689
      max_vma = MAX (vma, max_vma);
690
    }
691
 
692
  free (prev_name);
693
  free (prev_filename);
694
 
695
  /* Make room for function symbols, too.  */
696
  ltab.len += symtab.len;
697
  ltab.base = (Sym *) xmalloc (ltab.len * sizeof (Sym));
698
  ltab.limit = ltab.base;
699
 
700
  /* Pass 2 - create symbols.  */
701
 
702
  /* We now set is_static as we go along, rather than by running
703
     through the symbol table at the end.
704
 
705
     The old way called symtab_finalize before the is_static pass,
706
     causing a problem since symtab_finalize uses is_static as part of
707
     its address conflict resolution algorithm.  Since global symbols
708
     were prefered over static symbols, and all line symbols were
709
     global at that point, static function names that conflicted with
710
     their own line numbers (static, but labeled as global) were
711
     rejected in favor of the line num.
712
 
713
     This was not the desired functionality.  We always want to keep
714
     our function symbols and discard any conflicting line symbols.
715
     Perhaps symtab_finalize should be modified to make this
716
     distinction as well, but the current fix works and the code is a
717
     lot cleaner now.  */
718
  prev = 0;
719
 
720
  for (vma = core_text_sect->vma; vma < vma_high; vma += min_insn_size)
721
    {
722
      sym_init (ltab.limit);
723
 
724
      if (!get_src_info (vma, &filename, &ltab.limit->name, &ltab.limit->line_num)
725
          || (prev && prev->line_num == ltab.limit->line_num
726
              && strcmp (prev->name, ltab.limit->name) == 0
727
              && strcmp (prev->file->name, filename) == 0))
728
        continue;
729
 
730
      /* Make name pointer a malloc'ed string.  */
731
      ltab.limit->name = xstrdup (ltab.limit->name);
732
      ltab.limit->file = source_file_lookup_path (filename);
733
 
734
      ltab.limit->addr = vma;
735
 
736
      /* Set is_static based on the enclosing function, using either:
737
         1) the previous symbol, if it's from the same function, or
738
         2) a symtab lookup.  */
739
      if (prev && ltab.limit->file == prev->file &&
740
          strcmp (ltab.limit->name, prev->name) == 0)
741
        {
742
          ltab.limit->is_static = prev->is_static;
743
        }
744
      else
745
        {
746
          sym = sym_lookup(&symtab, ltab.limit->addr);
747
          ltab.limit->is_static = sym->is_static;
748
        }
749
 
750
      prev = ltab.limit;
751
 
752
      DBG (AOUTDEBUG, printf ("[core_create_line_syms] %lu %s 0x%lx\n",
753
                              (unsigned long) (ltab.limit - ltab.base),
754
                              ltab.limit->name,
755
                              (unsigned long) ltab.limit->addr));
756
      ++ltab.limit;
757
    }
758
 
759
  /* Update sentinels.  */
760
  sentinel = sym_lookup (&symtab, (bfd_vma) 0);
761
 
762
  if (sentinel
763
      && strcmp (sentinel->name, "<locore>") == 0
764
      && min_vma <= sentinel->end_addr)
765
    sentinel->end_addr = min_vma - 1;
766
 
767
  sentinel = sym_lookup (&symtab, ~(bfd_vma) 0);
768
 
769
  if (sentinel
770
      && strcmp (sentinel->name, "<hicore>") == 0
771
      && max_vma >= sentinel->addr)
772
    sentinel->addr = max_vma + 1;
773
 
774
  /* Copy in function symbols.  */
775
  memcpy (ltab.limit, symtab.base, symtab.len * sizeof (Sym));
776
  ltab.limit += symtab.len;
777
 
778
  if ((unsigned int) (ltab.limit - ltab.base) != ltab.len)
779
    {
780
      fprintf (stderr,
781
               _("%s: somebody miscounted: ltab.len=%d instead of %ld\n"),
782
               whoami, ltab.len, (long) (ltab.limit - ltab.base));
783
      done (1);
784
    }
785
 
786
  /* Finalize ltab and make it symbol table.  */
787
  symtab_finalize (&ltab);
788
  free (symtab.base);
789
  symtab = ltab;
790
}

powered by: WebSVN 2.1.0

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