2003-11-22 Andrew Cagney <cagney@redhat.com>

* mips-tdep.c (skip_prologue_using_sal): New function.
	(mips32_skip_prologue, mips16_skip_prologue): Use
	skip_prologue_using_sal to get an upper bound on the search.
This commit is contained in:
Andrew Cagney 2003-11-22 21:12:24 +00:00
parent dd625418be
commit 74da7425d5
2 changed files with 71 additions and 2 deletions

View File

@ -1,5 +1,9 @@
2003-11-22 Andrew Cagney <cagney@redhat.com>
* mips-tdep.c (skip_prologue_using_sal): New function.
(mips32_skip_prologue, mips16_skip_prologue): Use
skip_prologue_using_sal to get an upper bound on the search.
* config/powerpc/tm-linux.h (PROLOGUE_FIRSTLINE_OVERLAP): Delete
#if 0'ed macro.
* infrun.c (step_into_function): Delete #ifdef

View File

@ -4307,6 +4307,61 @@ mips_step_skips_delay (CORE_ADDR pc)
}
/* Given PC at the function's start address, attempt to find the
prologue end using SAL information. Return zero if the skip fails.
A non-optimized prologue traditionally has one SAL for the function
and a second for the function body. A single line function has
them both pointing at the same line.
An optimized prologue is similar but the prologue may contain
instructions (SALs) from the instruction body. Need to skip those
while not getting into the function body.
The functions end point and an increasing SAL line are used as
indicators of the prologue's endpoint.
This code is based on the function refine_prologue_limit (versions
found in both ia64 and ppc). */
static CORE_ADDR
skip_prologue_using_sal (CORE_ADDR func_addr)
{
struct symtab_and_line prologue_sal;
CORE_ADDR start_pc;
CORE_ADDR end_pc;
/* Get an initial range for the function. */
find_pc_partial_function (func_addr, NULL, &start_pc, &end_pc);
start_pc += FUNCTION_START_OFFSET;
prologue_sal = find_pc_line (start_pc, 0);
if (prologue_sal.line != 0)
{
while (prologue_sal.end < end_pc)
{
struct symtab_and_line sal;
sal = find_pc_line (prologue_sal.end, 0);
if (sal.line == 0)
break;
/* Assume that a consecutive SAL for the same (or larger)
line mark the prologue -> body transition. */
if (sal.line >= prologue_sal.line)
break;
/* The case in which compiler's optimizer/scheduler has
moved instructions into the prologue. We look ahead in
the function looking for address ranges whose
corresponding line number is less the first one that we
found for the function. This is more conservative then
refine_prologue_limit which scans a large number of SALs
looking for any in the prologue */
prologue_sal = sal;
}
}
return prologue_sal.end;
}
/* Skip the PC past function prologue instructions (32-bit version).
This is a helper function for mips_skip_prologue. */
@ -4318,10 +4373,15 @@ mips32_skip_prologue (CORE_ADDR pc)
int seen_sp_adjust = 0;
int load_immediate_bytes = 0;
/* Find an upper bound on the prologue. */
end_pc = skip_prologue_using_sal (pc);
if (end_pc == 0)
end_pc = pc + 100; /* Magic. */
/* Skip the typical prologue instructions. These are the stack adjustment
instruction and the instructions that save registers on the stack
or in the gcc frame. */
for (end_pc = pc + 100; pc < end_pc; pc += MIPS_INSTLEN)
for (; pc < end_pc; pc += MIPS_INSTLEN)
{
unsigned long high_word;
@ -4463,10 +4523,15 @@ mips16_skip_prologue (CORE_ADDR pc)
} /* end of table marker */
};
/* Find an upper bound on the prologue. */
end_pc = skip_prologue_using_sal (pc);
if (end_pc == 0)
end_pc = pc + 100; /* Magic. */
/* Skip the typical prologue instructions. These are the stack adjustment
instruction and the instructions that save registers on the stack
or in the gcc frame. */
for (end_pc = pc + 100; pc < end_pc; pc += MIPS16_INSTLEN)
for (; pc < end_pc; pc += MIPS16_INSTLEN)
{
unsigned short inst;
int i;