This is the mail archive of the gdb-patches@sources.redhat.com mailing list for the GDB project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[RFC] frv-tdep.c: Use refine_prologue_limit() instead ofskip_prologue_using_sal()


On FR-V, I've encountered an optimized prologue in which
skip_prologue_using_sal() fails to making it past the first
prologue -> body transition.  The prologue in question is not all that
unusual (for an optimized prologue) which leads me to wonder about the
efficacy of skip_prologue_using_sal() with regard to optimized
prologues in general.  I've read the comments and code in
skip_prologue_using_sal(), however, and it does seem to be operating
as intended.

That said, it seems like a shame to introduce yet another private copy
of refine_prologue_limit().  (Though I was careful to keep this one
the same as that defined in rs6000-tdep.c.  The IA-64 version differs
slightly.)  Perhaps it's time to move refine_prologue_limit to
symtab.c?  Or perhaps skip_prologue_using_sal() should be revised
somewhat so that it provides more useful results?

Comments?

	* frv-tdep.c (max_skip_non_prologue_insns): New static global.
	(refine_prologue_limit): New function copied verbatim from
	rs6000-tdep.c.
	(frv_analyze_prologue): Use refine_prologue_limit() instead of
	skip_prologue_using_sal().

Index: frv-tdep.c
===================================================================
RCS file: /cvs/src/src/gdb/frv-tdep.c,v
retrieving revision 1.87
diff -u -p -r1.87 frv-tdep.c
--- frv-tdep.c	20 Jul 2004 19:45:05 -0000	1.87
+++ frv-tdep.c	30 Jul 2004 21:25:10 -0000
@@ -504,6 +504,64 @@ is_argument_reg (int reg)
   return (8 <= reg && reg <= 13);
 }
 
+/* Limit the number of skipped non-prologue instructions, as the examining
+   of the prologue is expensive.  */
+static int max_skip_non_prologue_insns = 10;
+
+/* Given PC representing the starting address of a function, and
+   LIM_PC which is the (sloppy) limit to which to scan when looking
+   for a prologue, attempt to further refine this limit by using
+   the line data in the symbol table.  If successful, a better guess
+   on where the prologue ends is returned, otherwise the previous
+   value of lim_pc is returned.  */
+
+/* Note: cagney/2004-02-14: This function and logic have largely been
+   superseded by skip_prologue_using_sal.  
+   Note: kevinb/2004-07-29: Not true.  On FR-V, I've encountered a
+   case where skip_prologue_using_sal() doesn't make it past the
+   first prologue -> body transition.  */
+
+static CORE_ADDR
+refine_prologue_limit (CORE_ADDR pc, CORE_ADDR lim_pc)
+{
+  struct symtab_and_line prologue_sal;
+
+  prologue_sal = find_pc_line (pc, 0);
+  if (prologue_sal.line != 0)
+    {
+      int i;
+      CORE_ADDR addr = prologue_sal.end;
+
+      /* Handle the case in which compiler's optimizer/scheduler
+         has moved instructions into the prologue.  We scan ahead
+	 in the function looking for address ranges whose corresponding
+	 line number is less than or equal to the first one that we
+	 found for the function.  (It can be less than when the
+	 scheduler puts a body instruction before the first prologue
+	 instruction.)  */
+      for (i = 2 * max_skip_non_prologue_insns; 
+           i > 0 && (lim_pc == 0 || addr < lim_pc);
+	   i--)
+        {
+	  struct symtab_and_line sal;
+
+	  sal = find_pc_line (addr, 0);
+	  if (sal.line == 0)
+	    break;
+	  if (sal.line <= prologue_sal.line 
+	      && sal.symtab == prologue_sal.symtab)
+	    {
+	      prologue_sal = sal;
+	    }
+	  addr = sal.end;
+	}
+
+      if (lim_pc == 0 || prologue_sal.end < lim_pc)
+	lim_pc = prologue_sal.end;
+    }
+  return lim_pc;
+}
+
 /* Scan an FR-V prologue, starting at PC, until frame->PC.
    If FRAME is non-zero, fill in its saved_regs with appropriate addresses.
    We assume FRAME's saved_regs array has already been allocated and cleared.
@@ -573,17 +631,18 @@ frv_analyze_prologue (CORE_ADDR pc, stru
 
   last_prologue_pc = pc;
 
-  /* Try to compute an upper limit (on how far to scan) based on the
-     line number info.  */
-  lim_pc = skip_prologue_using_sal (pc);
-  /* If there's no line number info, lim_pc will be 0.  In that case,
-     set the limit to be 100 instructions away from pc.  Hopefully, this
-     will be far enough away to account for the entire prologue.  Don't
-     worry about overshooting the end of the function.  The scan loop
-     below contains some checks to avoid scanning unreasonably far.  */
+  /* Set the initial limit to be 100 instructions away from pc. 
+     Hopefully, this will be far enough away to account for the entire
+     prologue.  Don't worry about overshooting the end of the
+     function.  The scan loop below contains some checks to avoid
+     scanning unreasonably far.  */
   if (lim_pc == 0)
     lim_pc = pc + 400;
 
+  /* Attempt to refine (reduce) the limit based on available line number
+     info.  */
+  lim_pc = refine_prologue_limit (pc, lim_pc);
+
   /* If we have a frame, we don't want to scan past the frame's pc.  This
      will catch those cases where the pc is in the prologue.  */
   if (next_frame)


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]