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]

Porting h8300 - gdb frame to new frame code


Hi,
 Reference:http://sources.redhat.com/ml/gdb-patches/2004-07/msg00185.html

  I am in the task of porting h8300 to new frame structure. I have taken the ported 
"Sh" frame code as a reference for "h8300" porting.

I have introduced the new frame related functions as shown in the patch below.

Also the following function has been modified:
   h8300_examine_prologue

But while executing the command "info f" I am getting wrong location of args and locals 
(i.e. it is giving the location as the location of sp, where as is it should be the location 
of frame). I have changed only the "get_frame_base " argument in "h8300_examine_prologue" to 
the cache->base as it would be the location of stack address. 
 
Is it due to the fact that the generated dwarf 2 information for H8300 is not correct?

Any help in this regard will be appreciated.

===========================================================================================
--- gdb-6.2/gdb/h8300-tdep-old.c	2004-06-20 22:48:05.000000000 +0530
+++ gdb-6.2/gdb/h8300-tdep.c	2004-08-31 19:01:09.000000000 +0530
@@ -37,11 +37,12 @@
 #include "gdb_assert.h"
 #include "dis-asm.h"
 
-/* Extra info which is saved in each frame_info. */
-struct frame_extra_info
-{
-  CORE_ADDR from_pc;
-};
+#include "frame-unwind.h"
+#include "frame.h"
+#include "frame-base.h"
+#include "dwarf2-frame.h"
+
+#define H8300_NUM_REGS 35
 
 enum
 {
@@ -50,6 +51,21 @@
   h8300_max_reg_size = 4,
 };
 
+struct h8300_frame_cache
+{
+  /* Base address.  */
+  CORE_ADDR base;
+  LONGEST sp_offset;
+  CORE_ADDR pc;
+
+  /* Flag showing that a frame has been created in the prologue code. */
+  int uses_fp;
+
+  /* Saved registers.  */
+  CORE_ADDR saved_regs[H8300_NUM_REGS];
+  CORE_ADDR saved_sp;
+};
+
 static int is_h8300hmode (struct gdbarch *gdbarch);
 static int is_h8300smode (struct gdbarch *gdbarch);
 static int is_h8300sxmode (struct gdbarch *gdbarch);
@@ -327,242 +343,353 @@
    LOCALS1    <-SP POINTS HERE
  */
 
-static CORE_ADDR
-h8300_examine_prologue (CORE_ADDR ip, CORE_ADDR limit,
-			CORE_ADDR after_prolog_fp, CORE_ADDR *fsr,
-			struct frame_info *fi)
-{
-  CORE_ADDR next_ip;
+static CORE_ADDR
+h8300_examine_prologue (CORE_ADDR pc, CORE_ADDR current_pc,
+		     struct h8300_frame_cache *cache, int limit)
+{
+  
+  CORE_ADDR opc;
+  CORE_ADDR next_pc;
   int r;
-  int have_fp = 0;
-  unsigned short insn_word;
-  /* Number of things pushed onto stack, starts at 2/4, 'cause the
-     PC is already there */
-  unsigned int reg_save_depth = BINWORD;
-
-  unsigned int auto_depth = 0;	/* Number of bytes of autos */
-
-  char in_frame[11];		/* One for each reg */
-
+  
+ 
+  unsigned short insn_word;
+  /* Number of things pushed onto stack, starts at 2/4, 'cause the
+     PC is already there */
+  unsigned int reg_save_depth = BINWORD;
+
+  unsigned int auto_depth = 0;	/* Number of bytes of autos */
+
+  char in_frame[11];		/* One for each reg */
   int adjust = 0;
+ cache->uses_fp = 0;
 
-  memset (in_frame, 1, 11);
-  for (r = 0; r < 8; r++)
-    {
-      fsr[r] = 0;
-    }
-  if (after_prolog_fp == 0)
-    {
-      after_prolog_fp = read_register (E_SP_REGNUM);
-    }
+ 
+ if (pc >= current_pc)
+    return current_pc;
+
+  memset (in_frame, 1, 11);
 
-  /* If the PC isn't valid, quit now.  */
-  if (ip == 0 || ip & (is_h8300hmode (current_gdbarch) &&
-			 !is_h8300_normal_mode (current_gdbarch) ? ~0xffffff : ~0xffff))
+  if (pc == 0 || pc & (is_h8300hmode (current_gdbarch) &&
+			 !is_h8300_normal_mode (current_gdbarch) ? ~0xffffff : ~0xffff))
     return 0;
-
-  next_ip = h8300_next_prologue_insn (ip, limit, &insn_word);
-
-  if (insn_word == 0x0100)	/* mov.l */
-    {
-      insn_word = read_memory_unsigned_integer (ip + 2, 2);
-      adjust = 2;
+ 
+  
+   if (insn_word == 0x0100)	/* mov.l */
+    {
+      insn_word = read_memory_unsigned_integer (pc + 2, 2);
+      adjust = 2;
+    }
+
+  /* Skip over any fp push instructions */
+  cache->saved_regs[E_FP_REGNUM] = cache->base;
+  while (next_pc && IS_PUSH_FP (insn_word))
+    {
+      pc = next_pc + adjust;
+
+      in_frame[insn_word & 0x7] = reg_save_depth;
+      next_pc = h8300_next_prologue_insn (pc, limit, &insn_word);
+      reg_save_depth += 2 + adjust;
+    }
+    
+  /* Is this a move into the fp */
+  if (next_pc && IS_MOV_SP_FP (insn_word))
+    {
+      pc = next_pc;
+      next_pc = h8300_next_prologue_insn (pc, limit, &insn_word);
+      cache->uses_fp = 1;
+    }
+
+  /* Skip over any stack adjustment, happens either with a number of
+     sub#2,sp or a mov #x,r5 sub r5,sp */
+
+  if (next_pc && (IS_SUB2_SP (insn_word) || IS_SUB4_SP (insn_word)))
+    {
+      while (next_pc && (IS_SUB2_SP (insn_word) || IS_SUB4_SP (insn_word)))
+	{
+	   cache->sp_offset += IS_SUB2_SP (insn_word) ? 2 : 4;
+	  pc = next_pc;
+	  next_pc = h8300_next_prologue_insn (pc, limit, &insn_word);
+	}
+    }
+  else
+    {
+      if (next_pc && IS_MOVK_R5 (insn_word))
+	{
+	  pc = next_pc;
+	  next_pc = h8300_next_prologue_insn (pc, limit, &insn_word);
+	  cache->sp_offset += insn_word;
+
+	  next_pc = h8300_next_prologue_insn (next_pc, limit, &insn_word);
+	  cache->sp_offset += insn_word;
+	}
+      if (next_pc && IS_SUBL_SP (insn_word))
+	{
+	  pc = next_pc;
+	  cache->sp_offset += read_memory_unsigned_integer (pc, 4);
+	  pc += 4;
+
+	  next_pc = h8300_next_prologue_insn (pc, limit, &insn_word);
+	}
+    }
+
+  /* Now examine the push insns to determine where everything lives
+     on the stack.  */
+  while (1)
+    {
+      adjust = 0;
+      if (!next_pc)
+	break;
+
+      if (insn_word == 0x0100)
+	{
+	  pc = next_pc;
+	  next_pc = h8300_next_prologue_insn (pc, limit, &insn_word);
+	  adjust = 2;
+	}
+
+      if (IS_PUSH (insn_word))
+	{
+	  cache->sp_offset += 2 + adjust;
+	  cache->saved_regs[insn_word & 0x7] = cache->base - cache->sp_offset;
+	  pc = next_pc;
+	  next_pc = h8300_next_prologue_insn (pc, limit, &insn_word);
+	  continue;
+	}
+
+      /* Now check for push multiple insns.  */
+      if (insn_word == 0x0110 || insn_word == 0x0120 || insn_word == 0x0130)
+	{
+	  int count = ((insn_word >> 4) & 0xf) + 1;
+	  int start, i;
+
+	  pc = next_pc;
+	  next_pc = h8300_next_prologue_insn (pc, limit, &insn_word);
+	  start = insn_word & 0x7;
+
+	  for (i = start; i < start + count; i++)
+	    {
+	      cache->sp_offset += 4;
+	      cache->saved_regs[i] = cache->base - cache->sp_offset;
+	    }
+	}
+      break;
+    }
+
+  
+  /* Rememeber any others too */
+    cache->pc= read_memory_unsigned_integer (cache->base + BINWORD, BINWORD); 
+
+  in_frame[E_PC_REGNUM] = 0;
+
+  if (cache->uses_fp)
+    /* We keep the old FP in the SP spot */
+    cache->saved_sp = read_memory_unsigned_integer (cache->saved_regs[E_FP_REGNUM],
+						     BINWORD);
+  else
+    cache->saved_sp = cache->base + cache->sp_offset;
+
+
+  
+
+  return (pc);
+}
+
+static struct h8300_frame_cache *
+h8300_alloc_frame_cache (void)
+{
+  struct h8300_frame_cache *cache;
+  int i;
+
+  cache = FRAME_OBSTACK_ZALLOC (struct h8300_frame_cache);
+
+  /* Base address.  */
+  cache->base = 0;
+  cache->saved_sp = 0;
+  cache->sp_offset = 0;
+  cache->pc = 0;
+
+  /* Frameless until proven otherwise.  */
+  cache->uses_fp = 0;
+
+  /* Saved registers.  We initialize these to -1 since zero is a valid
+     offset (that's where fp is supposed to be stored).  */
+  for (i = 0; i < H8300_NUM_REGS; i++)
+    {
+      cache->saved_regs[i] = -1;
     }
 
-  /* Skip over any fp push instructions */
-  fsr[E_FP_REGNUM] = after_prolog_fp;
-  while (next_ip && IS_PUSH_FP (insn_word))
-    {
-      ip = next_ip + adjust;
+  return cache;
+}
 
-      in_frame[insn_word & 0x7] = reg_save_depth;
-      next_ip = h8300_next_prologue_insn (ip, limit, &insn_word);
-      reg_save_depth += 2 + adjust;
-    }
+static struct h8300_frame_cache *
+h8300_frame_cache (struct frame_info *next_frame, void **this_cache)
+{
+  struct h8300_frame_cache *cache;
+  CORE_ADDR current_pc;
+  
+  CORE_ADDR func_addr, func_end;
+  int i,limit;
 
-  /* Is this a move into the fp */
-  if (next_ip && IS_MOV_SP_FP (insn_word))
-    {
-      ip = next_ip;
-      next_ip = h8300_next_prologue_insn (ip, limit, &insn_word);
-      have_fp = 1;
-    }
+  if (*this_cache)
+    return *this_cache;
 
-  /* Skip over any stack adjustment, happens either with a number of
-     sub#2,sp or a mov #x,r5 sub r5,sp */
+  cache = h8300_alloc_frame_cache ();
+  *this_cache = cache;
 
-  if (next_ip && (IS_SUB2_SP (insn_word) || IS_SUB4_SP (insn_word)))
-    {
-      while (next_ip && (IS_SUB2_SP (insn_word) || IS_SUB4_SP (insn_word)))
-	{
-	  auto_depth += IS_SUB2_SP (insn_word) ? 2 : 4;
-	  ip = next_ip;
-	  next_ip = h8300_next_prologue_insn (ip, limit, &insn_word);
-	}
-    }
-  else
-    {
-      if (next_ip && IS_MOVK_R5 (insn_word))
-	{
-	  ip = next_ip;
-	  next_ip = h8300_next_prologue_insn (ip, limit, &insn_word);
-	  auto_depth += insn_word;
+  /* In principle, for normal frames, fp holds the frame pointer,
+     which holds the base address for the current stack frame.
+     However, for functions that don't need it, the frame pointer is
+     optional.  For these "frameless" functions the frame pointer is
+     actually the frame pointer of the calling frame. */
+  cache->base = frame_unwind_register_unsigned (next_frame, E_FP_REGNUM);
+  if (cache->base == 0)
+    return cache;
 
-	  next_ip = h8300_next_prologue_insn (next_ip, limit, &insn_word);
-	  auto_depth += insn_word;
-	}
-      if (next_ip && IS_SUBL_SP (insn_word))
-	{
-	  ip = next_ip;
-	  auto_depth += read_memory_unsigned_integer (ip, 4);
-	  ip += 4;
+  cache->pc = frame_func_unwind (next_frame);
+  current_pc = frame_pc_unwind (next_frame);
 
-	  next_ip = h8300_next_prologue_insn (ip, limit, &insn_word);
+  if (find_pc_partial_function (current_pc, NULL, 
+				    &func_addr, &func_end))
+        {
+	  struct symtab_and_line sal = find_pc_line (func_addr, 0);
+	  CORE_ADDR limit = (sal.end && sal.end < current_pc) 
+	    ? sal.end : current_pc;
+	  h8300_examine_prologue (cache->pc,current_pc, cache, limit );
 	}
-    }
-
-  /* Now examine the push insns to determine where everything lives
-     on the stack.  */
-  while (1)
+  if (!cache->uses_fp)
     {
-      adjust = 0;
-      if (!next_ip)
-	break;
-
-      if (insn_word == 0x0100)
-	{
-	  ip = next_ip;
-	  next_ip = h8300_next_prologue_insn (ip, limit, &insn_word);
-	  adjust = 2;
-	}
+      /* We didn't find a valid frame, which means that CACHE->base
+         currently holds the frame pointer for our calling frame.  If
+         we're at the start of a function, or somewhere half-way its
+         prologue, the function's frame probably hasn't been fully
+         setup yet.  Try to reconstruct the base address for the stack
+         frame by looking at the stack pointer.  For truly "frameless"
+         functions this might work too.  */
+      cache->base = frame_unwind_register_unsigned (next_frame, E_SP_REGNUM);
+    }
+
+  /* Now that we have the base address for the stack frame we can
+     calculate the value of sp in the calling frame.  */
+  cache->saved_regs[E_SP_REGNUM] = cache->base + cache->sp_offset ;
+
+  /* Adjust all the saved registers such that they contain addresses
+     instead of offsets.  */
+  for (i = 0; i < H8300_NUM_REGS; i++)
+    if (cache->saved_regs[i] != -1)
+      cache->saved_regs[i] = cache->saved_regs[E_SP_REGNUM] - cache->saved_regs[i] - BINWORD;
+    
+  return cache;
+}
 
-      if (IS_PUSH (insn_word))
+static void
+h8300_frame_prev_register (struct frame_info *next_frame, void **this_cache,
+			int regnum, int *optimizedp,
+			enum lval_type *lvalp, CORE_ADDR *addrp,
+			int *realnump, void *valuep)
+{
+  struct h8300_frame_cache *cache = h8300_frame_cache (next_frame, this_cache);
+
+  gdb_assert (regnum >= 0);
+
+  if (regnum == E_SP_REGNUM && cache->saved_regs[E_SP_REGNUM])
+    {
+      *optimizedp = 0;
+      *lvalp = not_lval;
+      *addrp = 0;
+      *realnump = -1;
+      if (valuep)
 	{
-	  auto_depth += 2 + adjust;
-	  fsr[insn_word & 0x7] = after_prolog_fp - auto_depth;
-	  ip = next_ip;
-	  next_ip = h8300_next_prologue_insn (ip, limit, &insn_word);
-	  continue;
+	  /* Store the value.  */
+	  store_unsigned_integer (valuep, BINWORD, cache->saved_regs[E_SP_REGNUM]);
 	}
+      return;
+    }
 
-      /* Now check for push multiple insns.  */
-      if (insn_word == 0x0110 || insn_word == 0x0120 || insn_word == 0x0130)
+  /* The PC of the previous frame is stored in the PR register of
+     the current frame.  Frob regnum so that we pull the value from
+     the correct place.  */
+  if (regnum == E_PC_REGNUM)
+    regnum = E_SP_REGNUM;
+
+  if (regnum < H8300_NUM_REGS && cache->saved_regs[regnum] != -1)
+    {
+      *optimizedp = 0;
+      *lvalp = lval_memory;
+      *addrp = cache->saved_regs[regnum];
+      *realnump = -1;
+      if (valuep)
 	{
-	  int count = ((insn_word >> 4) & 0xf) + 1;
-	  int start, i;
-
-	  ip = next_ip;
-	  next_ip = h8300_next_prologue_insn (ip, limit, &insn_word);
-	  start = insn_word & 0x7;
-
-	  for (i = start; i < start + count; i++)
-	    {
-	      auto_depth += 4;
-	      fsr[i] = after_prolog_fp - auto_depth;
-	    }
+	  /* Read the value in from memory.  */
+	  read_memory (*addrp, valuep,
+		       register_size (current_gdbarch, regnum));
 	}
-      break;
+      return;
     }
 
-  /* The PC is at a known place */
-  get_frame_extra_info (fi)->from_pc =
-    read_memory_unsigned_integer (after_prolog_fp + BINWORD, BINWORD);
-
-  /* Rememeber any others too */
-  in_frame[E_PC_REGNUM] = 0;
-
-  if (have_fp)
-    /* We keep the old FP in the SP spot */
-    fsr[E_SP_REGNUM] = read_memory_unsigned_integer (fsr[E_FP_REGNUM], 
-						     BINWORD);
-  else
-    fsr[E_SP_REGNUM] = after_prolog_fp + auto_depth;
-
-  return (ip);
+  frame_register_unwind (next_frame, regnum,
+			 optimizedp, lvalp, addrp, realnump, valuep);
 }
 
 static void
-h8300_frame_init_saved_regs (struct frame_info *fi)
+h8300_frame_this_id (struct frame_info *next_frame, void **this_cache,
+		  struct frame_id *this_id)
 {
-  CORE_ADDR func_addr, func_end;
+  struct h8300_frame_cache *cache = h8300_frame_cache (next_frame, this_cache);
 
-  if (!deprecated_get_frame_saved_regs (fi))
-    {
-      frame_saved_regs_zalloc (fi);
+  /* This marks the outermost frame.  */
+  if (cache->base == 0)
+    return;
 
-      /* Find the beginning of this function, so we can analyze its
-	 prologue. */
-      if (find_pc_partial_function (get_frame_pc (fi), NULL, 
-				    &func_addr, &func_end))
-        {
-	  struct symtab_and_line sal = find_pc_line (func_addr, 0);
-	  CORE_ADDR limit = (sal.end && sal.end < get_frame_pc (fi)) 
-	    ? sal.end : get_frame_pc (fi);
-	  /* This will fill in fields in fi. */
-	  h8300_examine_prologue (func_addr, limit, get_frame_base (fi),
-				  deprecated_get_frame_saved_regs (fi), fi);
-	}
-      /* Else we're out of luck (can't debug completely stripped code). 
-	 FIXME. */
-    }
+  *this_id = frame_id_build (cache->saved_regs[E_SP_REGNUM], cache->pc);
 }
 
-/* Given a GDB frame, determine the address of the calling function's
-   frame.  This will be used to create a new GDB frame struct, and
-   then DEPRECATED_INIT_EXTRA_FRAME_INFO and DEPRECATED_INIT_FRAME_PC
-   will be called for the new frame.
+static const struct frame_unwind h8300_frame_unwind = {
+  NORMAL_FRAME,
+  h8300_frame_this_id,
+  h8300_frame_prev_register
+};
 
-   For us, the frame address is its stack pointer value, so we look up
-   the function prologue to determine the caller's sp value, and
-   return it.  */
+static const struct frame_unwind *
+h8300_frame_sniffer (struct frame_info *next_frame)
+{
+  return &h8300_frame_unwind;
+}
 
 static CORE_ADDR
-h8300_frame_chain (struct frame_info *thisframe)
+h8300_unwind_sp (struct gdbarch *gdbarch, struct frame_info *next_frame)
 {
-  if (deprecated_pc_in_call_dummy (get_frame_pc (thisframe)))
-    {				/* initialize the from_pc now */
-      get_frame_extra_info (thisframe)->from_pc =
-	deprecated_read_register_dummy (get_frame_pc (thisframe),
-					get_frame_base (thisframe),
-					E_PC_REGNUM);
-      return get_frame_base (thisframe);
-    }
-  return deprecated_get_frame_saved_regs (thisframe)[E_SP_REGNUM];
+  return frame_unwind_register_unsigned (next_frame, E_SP_REGNUM);
 }
 
-/* Return the saved PC from this frame.
-
-   If the frame has a memory copy of SRP_REGNUM, use that.  If not,
-   just use the register SRP_REGNUM itself.  */
-
 static CORE_ADDR
-h8300_frame_saved_pc (struct frame_info *frame)
+h8300_unwind_pc (struct gdbarch *gdbarch, struct frame_info *next_frame)
 {
-  if (deprecated_pc_in_call_dummy (get_frame_pc (frame)))
-    return deprecated_read_register_dummy (get_frame_pc (frame),
-					   get_frame_base (frame),
-					   E_PC_REGNUM);
-  else
-    return get_frame_extra_info (frame)->from_pc;
+  return frame_unwind_register_unsigned (next_frame, E_PC_REGNUM);
 }
 
-static void
-h8300_init_extra_frame_info (int fromleaf, struct frame_info *fi)
+static struct frame_id
+h8300_unwind_dummy_id (struct gdbarch *gdbarch, struct frame_info *next_frame)
 {
-  if (!get_frame_extra_info (fi))
-    {
-      frame_extra_info_zalloc (fi, sizeof (struct frame_extra_info));
-      get_frame_extra_info (fi)->from_pc = 0;
-      
-      if (!get_frame_pc (fi))
-        {
-	  if (get_next_frame (fi))
-	    deprecated_update_frame_pc_hack (fi, h8300_frame_saved_pc (get_next_frame (fi)));
-	}
-      h8300_frame_init_saved_regs (fi);
-    }
+  return frame_id_build (h8300_unwind_sp (gdbarch, next_frame),
+			 frame_pc_unwind (next_frame));
 }
 
+static CORE_ADDR
+h8300_frame_base_address (struct frame_info *next_frame, void **this_cache)
+{
+  struct h8300_frame_cache *cache = h8300_frame_cache (next_frame, this_cache);
+
+  return cache->base;
+}
+
+static const struct frame_base h8300_frame_base = {
+  &h8300_frame_unwind,
+  h8300_frame_base_address,
+  h8300_frame_base_address,
+  h8300_frame_base_address
+};
+
 /* Function: push_dummy_call
    Setup the function arguments for calling a function in the inferior.
    In this discussion, a `word' is 16 bits on the H8/300s, and 32 bits
@@ -637,7 +764,7 @@
   int wordsize = BINWORD;
   int reg = E_ARG0_REGNUM;
   int argument;
-
+ 
   /* First, make sure the stack is properly aligned.  */
   sp = align_down (sp, wordsize);
 
@@ -721,43 +848,10 @@
   /* Update stack pointer.  */
   regcache_cooked_write_unsigned (regcache, E_SP_REGNUM, sp);
 
+
   return sp;
 }
 
-/* Function: h8300_pop_frame
-   Restore the machine to the state it had before the current frame 
-   was created.  Usually used either by the "RETURN" command, or by
-   call_function_by_hand after the dummy_frame is finished. */
-
-static void
-h8300_pop_frame (void)
-{
-  unsigned regno;
-  struct frame_info *frame = get_current_frame ();
-
-  if (deprecated_pc_in_call_dummy (get_frame_pc (frame)))
-    {
-      deprecated_pop_dummy_frame ();
-    }
-  else
-    {
-      for (regno = 0; regno < 8; regno++)
-	{
-	  /* Don't forget E_SP_REGNUM is a frame_saved_regs struct is the
-	     actual value we want, not the address of the value we want.  */
-	  if (deprecated_get_frame_saved_regs (frame)[regno] && regno != E_SP_REGNUM)
-	    write_register (regno,
-			    read_memory_integer 
-			    (deprecated_get_frame_saved_regs (frame)[regno], BINWORD));
-	  else if (deprecated_get_frame_saved_regs (frame)[regno] && regno == E_SP_REGNUM)
-	    write_register (regno, get_frame_base (frame) + 2 * BINWORD);
-	}
-
-      /* Don't forget to update the PC too!  */
-      write_register (E_PC_REGNUM, get_frame_extra_info (frame)->from_pc);
-    }
-  flush_cached_frames ();
-}
 
 /* Function: extract_return_value
    Figure out where in REGBUF the called function has left its return value.
@@ -1183,10 +1277,6 @@
   if (arches != NULL)
     return arches->gdbarch;
 
-#if 0
-  tdep = (struct gdbarch_tdep *) xmalloc (sizeof (struct gdbarch_tdep));
-#endif
-
   if (info.bfd_arch_info->arch != bfd_arch_h8300)
     return NULL;
 
@@ -1282,16 +1372,13 @@
   set_gdbarch_pseudo_register_read (gdbarch, h8300_pseudo_register_read);
   set_gdbarch_pseudo_register_write (gdbarch, h8300_pseudo_register_write);
 
-  /* NOTE: cagney/2002-12-06: This can be deleted when this arch is
-     ready to unwind the PC first (see frame.c:get_prev_frame()).  */
-  set_gdbarch_deprecated_init_frame_pc (gdbarch, deprecated_init_frame_pc_default);
-
+  
   /*
    * Basic register fields and methods.
    */
 
   set_gdbarch_sp_regnum (gdbarch, E_SP_REGNUM);
-  set_gdbarch_deprecated_fp_regnum (gdbarch, E_FP_REGNUM);
+  set_gdbarch_fp0_regnum (gdbarch, E_FP_REGNUM);
   set_gdbarch_pc_regnum (gdbarch, E_PC_REGNUM);
   set_gdbarch_register_type (gdbarch, h8300_register_type);
   set_gdbarch_print_registers_info (gdbarch, h8300_print_registers_info);
@@ -1302,16 +1389,6 @@
    */
   set_gdbarch_skip_prologue (gdbarch, h8300_skip_prologue);
 
-  set_gdbarch_deprecated_frame_init_saved_regs (gdbarch, 
-						h8300_frame_init_saved_regs);
-  set_gdbarch_deprecated_init_extra_frame_info (gdbarch, 
-						h8300_init_extra_frame_info);
-  set_gdbarch_deprecated_frame_chain (gdbarch, h8300_frame_chain);
-  set_gdbarch_deprecated_saved_pc_after_call (gdbarch, 
-					      h8300_saved_pc_after_call);
-  set_gdbarch_deprecated_frame_saved_pc (gdbarch, h8300_frame_saved_pc);
-  set_gdbarch_deprecated_pop_frame (gdbarch, h8300_pop_frame);
-
   /* 
    * Miscelany
    */
@@ -1336,6 +1413,17 @@
   /* Char is unsigned.  */
   set_gdbarch_char_signed (gdbarch, 0);
 
+  //New frame strusture related functions.
+  set_gdbarch_unwind_sp (gdbarch, h8300_unwind_sp);
+  set_gdbarch_unwind_pc (gdbarch, h8300_unwind_pc);
+  set_gdbarch_unwind_dummy_id (gdbarch, h8300_unwind_dummy_id);
+  frame_base_set_default (gdbarch, &h8300_frame_base);
+  
+  gdbarch_init_osabi (info, gdbarch);
+  frame_unwind_append_sniffer (gdbarch, dwarf2_frame_sniffer);
+  frame_unwind_append_sniffer (gdbarch, h8300_frame_sniffer);
+
+
   return gdbarch;
 }
 
============================================================================================ 
 
Thanks in advance

Regards,
Sherry Samuel,
KPIT Cummins InfoSystems Ltd.
Pune, India

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Free download of GNU based tool-chains for Renesas' SH and H8 Series.
The following site also offers free technical support to its users. 
Visit http://www.kpitgnutools.com for details. 
Latest versions of KPIT GNU tools are released on June 1, 2004.
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 


-----Original Message-----
From: Andrew Cagney [mailto:cagney@gnu.org]
Sent: Thursday, July 15, 2004 11:49 PM
To: Sherry Samuel
Cc: gdb-patches@sources.redhat.com
Subject: Re: [Patch H8/300] : Fix for crashing of gdb with" info f"
command


> Hi
> Reference:http://sources.redhat.com/ml/gdb-patches/2004-06/msg00428.html
> 
> In the latest GDB(gdb+dejagnu-20040630) snap shot, the "info f" problem described in the above link is fixed. Referring through the links you have suggested, it is evident that h8300 target is not in the list of the new GDB frame structure. Is it possible to know what should be done from our side to update H8300 targets to the new frame work? Can you suggest how to go about it?
> 
> Thanks in advance.

Right,

A very simplistic cookbook is as follows:

- #if 0 all the set_gdbarch_deprecated ... lines
- build gdb
- try gdb on a simple program
   break main, info registers, stepi, nexti, ...
- fix an internal error due to missing method
- repeat

eventually you'll get gdb kind of working, at that point repeat the 
above using the testsuite.

It turns out that for architectures like this that use all the old 
deprecated methods, its quicker / easier to clear the deck and implement 
a new (borrowing heavily from the old code of course).

It also turns out that basic operations (break main; run, stepi, info 
registers) don't even need a frame unwinder - so that can be left as a 
separate pass.

For the unwinder, you need to convert the frame_saved_regs code into the 
frame_unwind_cache code (seen in more up-to-date architectures).

As for contributing this, perhaphs we can just incrementally submit the 
above in realtime?

Andrew





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