* infcmd.c (step_over_calls): Improve comments.
* symtab.c (find_pc_psymtab): Clean up a bit. * (find_pc_symtab): Fix comments, clean up code. * (find_pc_line): General cleanups, efficiency improvements. Also, don't return garbage when some line info exists, but there was no good match.
This commit is contained in:
parent
238f5383d0
commit
c1878f8788
2 changed files with 114 additions and 70 deletions
|
@ -1,3 +1,12 @@
|
|||
Fri Nov 13 20:24:10 1992 Stu Grossman (grossman at cygnus.com)
|
||||
|
||||
* infcmd.c (step_over_calls): Improve comments.
|
||||
* symtab.c (find_pc_psymtab): Clean up a bit.
|
||||
* (find_pc_symtab): Fix comments, clean up code.
|
||||
* (find_pc_line): General cleanups, efficiency improvements.
|
||||
Also, don't return garbage when some line info exists, but there
|
||||
was no good match.
|
||||
|
||||
Wed Nov 11 17:09:17 1992 Stu Grossman (grossman at cygnus.com)
|
||||
|
||||
* Makefile.in: Remove dependancies for 29k-share/dfe/yank.o and
|
||||
|
|
173
gdb/symtab.c
173
gdb/symtab.c
|
@ -372,10 +372,8 @@ find_pc_psymtab (pc)
|
|||
|
||||
ALL_PSYMTABS (objfile, pst)
|
||||
{
|
||||
if (pc >= pst -> textlow && pc < pst -> texthigh)
|
||||
{
|
||||
return (pst);
|
||||
}
|
||||
if (pc >= pst->textlow && pc < pst->texthigh)
|
||||
return (pst);
|
||||
}
|
||||
return (NULL);
|
||||
}
|
||||
|
@ -836,6 +834,8 @@ lookup_partial_symbol (pst, name, global, namespace)
|
|||
}
|
||||
|
||||
/* Find the psymtab containing main(). */
|
||||
/* FIXME: What about languages without main() or specially linked
|
||||
executables that have no main() ? */
|
||||
|
||||
struct partial_symtab *
|
||||
find_main_psymtab ()
|
||||
|
@ -961,7 +961,8 @@ block_function (bl)
|
|||
return BLOCK_FUNCTION (bl);
|
||||
}
|
||||
|
||||
/* Subroutine of find_pc_line */
|
||||
/* Find the symtab associated with PC. Look through the psymtabs and read in
|
||||
another symtab if necessary. */
|
||||
|
||||
struct symtab *
|
||||
find_pc_symtab (pc)
|
||||
|
@ -981,24 +982,16 @@ find_pc_symtab (pc)
|
|||
b = BLOCKVECTOR_BLOCK (bv, GLOBAL_BLOCK);
|
||||
if (BLOCK_START (b) <= pc
|
||||
&& BLOCK_END (b) > pc)
|
||||
goto found;
|
||||
return (s);
|
||||
}
|
||||
|
||||
if (!s)
|
||||
ps = find_pc_psymtab (pc);
|
||||
if (ps)
|
||||
{
|
||||
ps = find_pc_psymtab (pc);
|
||||
if (ps && ps->readin)
|
||||
{
|
||||
printf_filtered ("(Internal error: pc 0x%x in read in psymtab, but not in symtab.)\n", pc);
|
||||
}
|
||||
if (ps)
|
||||
{
|
||||
s = PSYMTAB_TO_SYMTAB (ps);
|
||||
}
|
||||
if (ps->readin)
|
||||
printf_filtered ("(Internal error: pc 0x%x in read in psymtab, but not in symtab.)\n", pc);
|
||||
s = PSYMTAB_TO_SYMTAB (ps);
|
||||
}
|
||||
|
||||
found:
|
||||
return (s);
|
||||
}
|
||||
|
||||
/* Find the source file and line number for a given PC value.
|
||||
|
@ -1018,14 +1011,13 @@ find_pc_line (pc, notcurrent)
|
|||
register struct linetable *l;
|
||||
register int len;
|
||||
register int i;
|
||||
register struct linetable_entry *item;
|
||||
register struct linetable_entry item;
|
||||
struct symtab_and_line val;
|
||||
struct blockvector *bv;
|
||||
|
||||
/* Info on best line seen so far, and where it starts, and its file. */
|
||||
|
||||
int best_line = 0;
|
||||
CORE_ADDR best_pc = 0;
|
||||
struct linetable_entry best;
|
||||
CORE_ADDR best_end = 0;
|
||||
struct symtab *best_symtab = 0;
|
||||
|
||||
|
@ -1034,19 +1026,17 @@ find_pc_line (pc, notcurrent)
|
|||
If we don't find a line whose range contains PC,
|
||||
we will use a line one less than this,
|
||||
with a range from the start of that file to the first line's pc. */
|
||||
int alt_line = 0;
|
||||
CORE_ADDR alt_pc = 0;
|
||||
struct linetable_entry alt;
|
||||
struct symtab *alt_symtab = 0;
|
||||
|
||||
/* Info on best line seen in this file. */
|
||||
|
||||
int prev_line;
|
||||
CORE_ADDR prev_pc;
|
||||
struct linetable_entry prev;
|
||||
|
||||
/* Info on first line of this file. */
|
||||
|
||||
int first_line;
|
||||
CORE_ADDR first_pc;
|
||||
best.line = 0;
|
||||
best.pc = 0;
|
||||
alt.line = 0;
|
||||
alt.pc = 0;
|
||||
|
||||
/* If this pc is not from the current frame,
|
||||
it is the address of the end of a call instruction.
|
||||
|
@ -1057,7 +1047,7 @@ find_pc_line (pc, notcurrent)
|
|||
if (notcurrent) pc -= 1;
|
||||
|
||||
s = find_pc_symtab (pc);
|
||||
if (s == 0)
|
||||
if (!s)
|
||||
{
|
||||
val.symtab = 0;
|
||||
val.line = 0;
|
||||
|
@ -1079,65 +1069,81 @@ find_pc_line (pc, notcurrent)
|
|||
if (!l)
|
||||
continue;
|
||||
len = l->nitems;
|
||||
prev_line = -1;
|
||||
first_line = -1;
|
||||
if (len <= 0)
|
||||
{
|
||||
fprintf (stderr, "Inconsistent line number info for %s\n",
|
||||
s->filename);
|
||||
continue;
|
||||
}
|
||||
|
||||
prev.line = -1;
|
||||
item = l->item[0]; /* Get first line info */
|
||||
|
||||
/* Is this file's first line closer than the first lines of other files?
|
||||
If so, record this file, and its first line, as best alternate. */
|
||||
if (item.pc > pc && (alt.pc == 0 || item.pc < alt.pc))
|
||||
{
|
||||
alt = item;
|
||||
alt_symtab = s;
|
||||
}
|
||||
|
||||
for (i = 0; i < len; i++)
|
||||
{
|
||||
item = &(l->item[i]);
|
||||
item = l->item[i];
|
||||
|
||||
if (first_line < 0)
|
||||
{
|
||||
first_line = item->line;
|
||||
first_pc = item->pc;
|
||||
}
|
||||
/* Return the last line that did not start after PC. */
|
||||
if (pc >= item->pc)
|
||||
{
|
||||
prev_line = item->line;
|
||||
prev_pc = item->pc;
|
||||
}
|
||||
else
|
||||
if (item.pc > pc)
|
||||
break;
|
||||
|
||||
prev = item;
|
||||
}
|
||||
|
||||
/* At this point, prev points at the line whose start addr is <= pc, and
|
||||
item points at the next line. If we ran off the end of the linetable
|
||||
(pc >= start of the last line), then prev == item. If pc < start of
|
||||
the first line, prev will not be set. */
|
||||
|
||||
/* Is this file's best line closer than the best in the other files?
|
||||
If so, record this file, and its best line, as best so far. */
|
||||
if (prev_line >= 0 && prev_pc > best_pc)
|
||||
|
||||
if (prev.line >= 0 && prev.pc > best.pc)
|
||||
{
|
||||
best_pc = prev_pc;
|
||||
best_line = prev_line;
|
||||
best = prev;
|
||||
best_symtab = s;
|
||||
/* If another line is in the linetable, and its PC is closer
|
||||
than the best_end we currently have, take it as best_end. */
|
||||
if (i < len && (best_end == 0 || best_end > item->pc))
|
||||
best_end = item->pc;
|
||||
}
|
||||
/* Is this file's first line closer than the first lines of other files?
|
||||
If so, record this file, and its first line, as best alternate. */
|
||||
if (first_line >= 0 && first_pc > pc
|
||||
&& (alt_pc == 0 || first_pc < alt_pc))
|
||||
{
|
||||
alt_pc = first_pc;
|
||||
alt_line = first_line;
|
||||
alt_symtab = s;
|
||||
if (i < len && (best_end == 0 || best_end > item.pc))
|
||||
best_end = item.pc;
|
||||
}
|
||||
}
|
||||
if (best_symtab == 0)
|
||||
|
||||
if (!best_symtab)
|
||||
{
|
||||
val.symtab = alt_symtab;
|
||||
val.line = alt_line - 1;
|
||||
val.pc = BLOCK_END (BLOCKVECTOR_BLOCK (bv, GLOBAL_BLOCK));
|
||||
val.end = alt_pc;
|
||||
if (!alt_symtab)
|
||||
{ /* If we didn't find any line # info, just
|
||||
return zeros. */
|
||||
val.symtab = 0;
|
||||
val.line = 0;
|
||||
val.pc = pc;
|
||||
val.end = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
val.symtab = alt_symtab;
|
||||
val.line = alt.line - 1;
|
||||
val.pc = BLOCK_END (BLOCKVECTOR_BLOCK (bv, GLOBAL_BLOCK));
|
||||
val.end = alt.pc;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
val.symtab = best_symtab;
|
||||
val.line = best_line;
|
||||
val.pc = best_pc;
|
||||
if (best_end && (alt_pc == 0 || best_end < alt_pc))
|
||||
val.line = best.line;
|
||||
val.pc = best.pc;
|
||||
if (best_end && (alt.pc == 0 || best_end < alt.pc))
|
||||
val.end = best_end;
|
||||
else if (alt_pc)
|
||||
val.end = alt_pc;
|
||||
else if (alt.pc)
|
||||
val.end = alt.pc;
|
||||
else
|
||||
val.end = BLOCK_END (BLOCKVECTOR_BLOCK (bv, GLOBAL_BLOCK));
|
||||
}
|
||||
|
@ -1484,7 +1490,36 @@ decode_line_1 (argptr, funfirstline, default_symtab, default_line)
|
|||
int default_line;
|
||||
{
|
||||
struct symtabs_and_lines values;
|
||||
#ifdef HPPA_COMPILER_BUG
|
||||
/* FIXME: The native HP 9000/700 compiler has a bug which appears
|
||||
when optimizing this file with target i960-vxworks. I haven't
|
||||
been able to construct a simple test case. The problem is that
|
||||
in the second call to SKIP_PROLOGUE below, the compiler somehow
|
||||
does not realize that the statement val = find_pc_line (...) will
|
||||
change the values of the fields of val. It extracts the elements
|
||||
into registers at the top of the block, and does not update the
|
||||
registers after the call to find_pc_line. You can check this by
|
||||
inserting a printf at the end of find_pc_line to show what values
|
||||
it is returning for val.pc and val.end and another printf after
|
||||
the call to see what values the function actually got (remember,
|
||||
this is compiling with cc -O, with this patch removed). You can
|
||||
also examine the assembly listing: search for the second call to
|
||||
skip_prologue; the LDO statement before the next call to
|
||||
find_pc_line loads the address of the structure which
|
||||
find_pc_line will return; if there is a LDW just before the LDO,
|
||||
which fetches an element of the structure, then the compiler
|
||||
still has the bug.
|
||||
|
||||
Setting val to volatile avoids the problem. We must undef
|
||||
volatile, because the HPPA native compiler does not define
|
||||
__STDC__, although it does understand volatile, and so volatile
|
||||
will have been defined away in defs.h. */
|
||||
#undef volatile
|
||||
volatile struct symtab_and_line val;
|
||||
#define volatile /*nothing*/
|
||||
#else
|
||||
struct symtab_and_line val;
|
||||
#endif
|
||||
register char *p, *p1;
|
||||
char *q, *q1;
|
||||
register struct symtab *s;
|
||||
|
|
Loading…
Add table
Reference in a new issue