* coffread.c (read_enum_type): Use the size of a target int when
authorSteve Chamberlain <sac@cygnus>
Thu, 6 Feb 1992 20:03:31 +0000 (20:03 +0000)
committerSteve Chamberlain <sac@cygnus>
Thu, 6 Feb 1992 20:03:31 +0000 (20:03 +0000)
describing enum.
* defs.h: added new #define for TARGET_PTR_BIT, defaults to size
of target int.
* h8300-tdep.c, remote-hms.c, tm-h8300.h: too many changes to count
* symtab.c (lookup_reference_type, lookup_ptr_type): use
TARGET_PTR_BIT to determine size of a pointer
* values.c (unpack_long): when unpacking a REF or a PTR don't
assume the size of the type.

gdb/ChangeLog
gdb/h8300-tdep.c
gdb/remote-hms.c
gdb/tm-h8300.h
gdb/values.c

index 5a7f16616ed13243cafa10ec84748af062dcf60d..97e9893f9f899cd711b66d283b2f7eb708e86cb6 100644 (file)
@@ -1,3 +1,15 @@
+Thu Feb  6 11:51:39 1992  Steve Chamberlain  (sac at rtl.cygnus.com)
+
+       * coffread.c (read_enum_type): Use the size of a target int when
+       describing enum.
+       * defs.h: added new #define for TARGET_PTR_BIT, defaults to size
+       of target int.
+       * h8300-tdep.c, remote-hms.c, tm-h8300.h: too many changes to count
+       * symtab.c (lookup_reference_type, lookup_ptr_type): use
+       TARGET_PTR_BIT to determine size of a pointer
+       * values.c (unpack_long): when unpacking a REF or a PTR don't
+       assume the size of the type.
+
 Wed Feb  5 22:29:59 1992  John Gilmore  (gnu at cygnus.com)
 
        * mipsread.c (parse_symbol):  Avoid clobbering enum pointer when
index 50a0092406617855c3f34b44e9c587e89043a510..4983e349ee19c4fcc9263339b2cfed4950ebbefb 100644 (file)
@@ -1,5 +1,33 @@
+/* Target-machine dependent code for Hitachi H8/300, for GDB.
+   Copyright (C) 1988, 1990, 1991 Free Software Foundation, Inc.
+
+This file is part of GDB.
+
+This program is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program; if not, write to the Free Software
+Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.  */
+
+/* 
+ Contributed by Steve Chamberlain
+                sac@cygnus.com 
+ */
+
 #include <stdio.h>
 #include "defs.h"
+#include "frame.h"
+#include "obstack.h"
+#include "symtab.h"
+#define UNSIGNED_SHORT(X) ((X) & 0xffff)
 
 /* an easy to debug H8 stack frame looks like:
 0x6df2 push    r2
                          subs  r5,sp
 
  */
+
 #define IS_PUSH(x) ((x & 0xff00)==0x6d00)
+#define IS_MOVE_FP(x) (x == 0x0d76)
+#define IS_MOV_SP_FP(x) (x == 0x0d76)
+#define IS_SUB2_SP(x) (x==0x1b87)
+#define IS_MOVK_R5(x) (x==0x7905)
+CORE_ADDR examine_prologue();
+
+void   frame_find_saved_regs ();
 CORE_ADDR h8300_skip_prologue(start_pc)
 CORE_ADDR start_pc;
 
 {
+
   /* Skip past all push insns */
   short int w;
   
@@ -24,16 +61,18 @@ CORE_ADDR start_pc;
     start_pc+=2;  
     w = read_memory_integer(start_pc, 2);
   }
-return start_pc;  
-  
-}
 
-h8300_pop_frame()
-{
-  printf("pop frame\n");
+  /* Skip past a move to FP */
+  if (IS_MOVE_FP(w)) {
+      start_pc +=2 ;
+      w = read_memory_integer(start_pc, 2);
+    }
+
+  return start_pc;  
   
 }
 
+
 int
 print_insn(memaddr, stream)
 CORE_ADDR memaddr;
@@ -42,18 +81,316 @@ FILE *stream;
   /* Nothing is bigger than 8 bytes */
   char   data[8];
   read_memory (memaddr, data, sizeof(data));
-  return print_insn_h8300(memaddr,  data   , stream);
-     
-     
+  return print_insn_h8300(memaddr,  data, stream);
 }
      
      
+/* 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
+   INIT_EXTRA_FRAME_INFO and INIT_FRAME_PC will be called for the new frame.
+
+   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.  */
+
+FRAME_ADDR
+FRAME_CHAIN (thisframe)
+     FRAME thisframe;
+{
+
+  frame_find_saved_regs (thisframe, (struct frame_saved_regs *) 0);
+    return thisframe->fsr->regs[SP_REGNUM];
+}
+
      
-     FRAME_CHAIN()
-     {
-     
-     printf("Frame chain\n");
-     
-     }
-     
+
+/* Put here the code to store, into a struct frame_saved_regs,
+   the addresses of the saved registers of frame described by FRAME_INFO.
+   This includes special registers such as pc and fp saved in special
+   ways in the stack frame.  sp is even more special:
+   the address we return for it IS the sp for the next frame.
+
+   We cache the result of doing this in the frame_cache_obstack, since
+   it is fairly expensive.  */
+
+void
+frame_find_saved_regs (fi, fsr)
+     struct frame_info *fi;
+     struct frame_saved_regs *fsr;
+{
+  register CORE_ADDR next_addr;
+  register CORE_ADDR *saved_regs;
+  register int regnum;
+  register struct frame_saved_regs *cache_fsr;
+  extern struct obstack frame_cache_obstack;
+  CORE_ADDR ip;
+  struct symtab_and_line sal;
+  CORE_ADDR limit;
+
+  if (!fi->fsr)
+    {
+      cache_fsr = (struct frame_saved_regs *)
+                 obstack_alloc (&frame_cache_obstack,
+                                sizeof (struct frame_saved_regs));
+      bzero (cache_fsr, sizeof (struct frame_saved_regs));
+      fi->fsr = cache_fsr;
+
+      /* Find the start and end of the function prologue.  If the PC
+        is in the function prologue, we only consider the part that
+        has executed already.  */
+         
+      ip = get_pc_function_start (fi->pc);
+      sal = find_pc_line (ip, 0);
+      limit = (sal.end && sal.end < fi->pc) ? sal.end: fi->pc;
+
+      /* This will fill in fields in *fi as well as in cache_fsr.  */
+      examine_prologue (ip, limit, fi->frame, cache_fsr, fi);
+    }
+
+  if (fsr)
+    *fsr = *fi->fsr;
+}
      
+
+/* Fetch the instruction at ADDR, returning 0 if ADDR is beyond LIM or
+   is not the address of a valid instruction, the address of the next
+   instruction beyond ADDR otherwise.  *PWORD1 receives the first word
+   of the instruction.*/
+
+
+CORE_ADDR
+NEXT_PROLOGUE_INSN(addr, lim, pword1)
+CORE_ADDR addr;
+CORE_ADDR lim;
+short *pword1;
+{
+  if (addr < lim+8)   
+  {
+    read_memory (addr, pword1, sizeof(*pword1));
+    SWAP_TARGET_AND_HOST (pword1, sizeof (short));
+    return addr + 2;
+  }
+
+  return 0;
+
+}
+
+/* Examine the prologue of a function.  `ip' points to the first instruction.
+   `limit' is the limit of the prologue (e.g. the addr of the first 
+   linenumber, or perhaps the program counter if we're stepping through).
+   `frame_sp' is the stack pointer value in use in this frame.  
+   `fsr' is a pointer to a frame_saved_regs structure into which we put
+   info about the registers saved by this frame.  
+   `fi' is a struct frame_info pointer; we fill in various fields in it
+   to reflect the offsets of the arg pointer and the locals pointer.  */
+
+/* We will find two sorts of prologue, framefull and non framefull:
+   
+   push   r2
+   push   r3
+   push   fp
+   mov    sp,fp
+   stack_ad
+   and
+   push   x
+   push   y
+   stack_ad
+
+*/
+
+static CORE_ADDR
+examine_prologue (ip, limit, after_prolog_fp, fsr, fi)
+     register CORE_ADDR ip;
+     register CORE_ADDR limit;
+     FRAME_ADDR after_prolog_fp;
+     struct frame_saved_regs *fsr;
+     struct frame_info *fi;
+{
+  register CORE_ADDR next_ip;
+  int r;
+  int i;
+  int have_fp = 0;
+  
+  register int src;
+  register struct pic_prologue_code *pcode;
+  INSN_WORD insn_word;
+  int size, offset;
+  unsigned int reg_save_depth = 2; /* Number of things pushed onto
+                                     stack, starts at 2, 'cause the
+                                     PC is already there */
+
+  unsigned int auto_depth = 0; /* Number of bytes of autos */
+  
+  char in_frame[NUM_REGS];      /* One for each reg */
+  
+  memset(in_frame, 1, NUM_REGS);
+  
+  if (after_prolog_fp == 0) {
+      after_prolog_fp = read_register(SP_REGNUM);
+    }  
+  if (ip == 0 || ip & ~0xffff) return 0;
+
+  next_ip = NEXT_PROLOGUE_INSN (ip, limit, &insn_word);
+
+  /* Skip over any push instructions, and remember where they were saved */
+
+
+  while (next_ip && IS_PUSH(insn_word))
+  {
+    ip = next_ip;
+    in_frame[insn_word & 0x7] = reg_save_depth;
+    next_ip = NEXT_PROLOGUE_INSN(ip, limit, &insn_word);
+    reg_save_depth +=2;
+
+  }
+  
+
+  /* Is this a move into the fp */
+  if (next_ip && IS_MOV_SP_FP(insn_word)) 
+  {
+    ip = next_ip;
+    next_ip = NEXT_PROLOGUE_INSN(ip, limit, &insn_word);
+    have_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_ip && IS_SUB2_SP(insn_word))
+  {
+    while (next_ip && IS_SUB2_SP(insn_word)) 
+    {
+      auto_depth +=2 ;
+      ip = next_ip;
+      next_ip = NEXT_PROLOGUE_INSN(ip, limit, &insn_word);
+    }
+  }
+  else  
+  {
+    if (next_ip && IS_MOVK_R5(insn_word)) 
+    {
+      ip = next_ip;
+      next_ip = NEXT_PROLOGUE_INSN(ip, limit, &insn_word);
+      auto_depth += insn_word;
+      ip +=4;
+      
+    }
+  }
+
+
+  
+  /* The args are always reffed based from the stack pointer */
+  fi->args_pointer =  after_prolog_fp - auto_depth;
+  /* Locals are always reffed based from the fp */
+  fi->locals_pointer = after_prolog_fp ;
+  /* The PC is at a known place */
+  fi->from_pc = read_memory_integer(after_prolog_fp + reg_save_depth-2 , 2);
+  
+
+  /* Rememeber any others too */
+
+  in_frame[PC_REGNUM] = 0;
+  
+  for (r = 0; r < NUM_REGS; r++) 
+  {
+    if (in_frame[r] != 1) 
+    {
+      fsr->regs[r] = after_prolog_fp + reg_save_depth - in_frame[r] -2;
+    }
+    else
+    {
+      fsr->regs[r] = 0;
+    }
+  }    
+  if (have_fp) 
+   /* We keep the old FP in the SP spot */
+   fsr->regs[SP_REGNUM] = read_memory_integer(fsr->regs[6],2);
+  else 
+   fsr->regs[SP_REGNUM] = after_prolog_fp + reg_save_depth;
+  
+  return (ip);
+}
+
+void
+init_extra_frame_info (fromleaf, fi)
+     int fromleaf;
+     struct frame_info *fi;
+{
+  fi->fsr = 0;                 /* Not yet allocated */
+  fi->args_pointer = 0;                /* Unknown */
+  fi->locals_pointer = 0;      /* Unknown */
+  fi->from_pc = 0;
+  
+}
+/* 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.  */
+
+CORE_ADDR
+frame_saved_pc (frame)
+FRAME frame;
+
+{
+  return frame->from_pc;
+}
+
+
+CORE_ADDR
+frame_locals_address (fi)
+     struct frame_info *fi;
+{
+  if (!fi->locals_pointer) 
+  {
+    struct frame_saved_regs ignore;
+    get_frame_saved_regs(fi, &ignore);  
+
+  }
+  return fi->locals_pointer;
+}
+
+/* Return the address of the argument block for the frame
+   described by FI.  Returns 0 if the address is unknown.  */
+
+CORE_ADDR
+frame_args_address (fi)
+     struct frame_info *fi;
+{
+  if (!fi->args_pointer) 
+  {
+    struct frame_saved_regs ignore;
+  get_frame_saved_regs(fi, &ignore);  
+
+  }
+  
+  return fi->args_pointer;
+}
+
+
+void h8300_pop_frame()
+{
+  unsigned regnum;
+  struct frame_saved_regs fsr;
+  struct frame_info *fi;
+
+  FRAME frame = get_current_frame();  
+  fi = get_frame_info(frame);  
+  get_frame_saved_regs(fi, &fsr);
+
+  for (regnum = 0; regnum < NUM_REGS; regnum ++) 
+  {
+    if(fsr.regs[regnum]) 
+    {
+      write_register(regnum, read_memory_integer (fsr.regs[regnum], 2));
+    }
+  
+    flush_cached_frames();
+    set_current_frame(create_new_frame(read_register(FP_REGNUM),
+                                      read_pc()));
+  
+  }
+
+}
index 19df1277ec8078f3dd031cfad63f6cf45b8129e5..48df7a7bfaa925cf0f2c998525ac138b88916b7a 100644 (file)
@@ -1,4 +1,4 @@
-/* Remote debugging interface for HMS  Monitor Version 1.0
+/* Remote debugging interface for Hitachi HMS Monitor Version 1.0
 
    Copyright 1992 Free Software Foundation, Inc.
 
@@ -55,22 +55,197 @@ static int  hms_clear_breakpoints();
 
 extern struct target_ops hms_ops;
 
-#define DEBUG  
+static int quiet = 1;
+
 #ifdef DEBUG
-# define DENTER(NAME)   (printf_filtered("Entering %s\n",NAME), fflush(stdout))
-# define DEXIT(NAME)    (printf_filtered("Exiting  %s\n",NAME), fflush(stdout))
+# define DENTER(NAME) if (!quiet)  (printf_filtered("Entering %s\n",NAME), fflush(stdout))
+# define DEXIT(NAME)  if (!quiet)  (printf_filtered("Exiting  %s\n",NAME), fflush(stdout))
 #else
 # define DENTER(NAME)
 # define DEXIT(NAME)
 #endif
 
 
+/***********************************************************************/
+/* Caching stuff stolen from remote-nindy.c  */
+
+/* The data cache records all the data read from the remote machine
+   since the last time it stopped.
+
+   Each cache block holds LINE_SIZE bytes of data
+   starting at a multiple-of-LINE_SIZE address.  */
+
+
+#define LINE_SIZE_POWER 4
+#define LINE_SIZE (1<<LINE_SIZE_POWER)     /* eg 1<<3 == 8 */
+#define LINE_SIZE_MASK ((LINE_SIZE-1))      /* eg 7*2+1= 111*/
+#define DCACHE_SIZE 64         /* Number of cache blocks */
+#define XFORM(x)  ((x&LINE_SIZE_MASK)>>2)
+struct dcache_block {
+       struct dcache_block *next, *last;
+       unsigned int addr;      /* Address for which data is recorded.  */
+       int data[LINE_SIZE/sizeof(int)];
+};
+
+struct dcache_block dcache_free, dcache_valid;
+
+/* Free all the data cache blocks, thus discarding all cached data.  */ 
+static
+void
+dcache_flush ()
+{
+  register struct dcache_block *db;
+
+  while ((db = dcache_valid.next) != &dcache_valid)
+    {
+      remque (db);
+      insque (db, &dcache_free);
+    }
+}
+
+/*
+ * If addr is present in the dcache, return the address of the block
+ * containing it.
+ */
+static
+struct dcache_block *
+dcache_hit (addr)
+     unsigned int addr;
+{
+  register struct dcache_block *db;
+
+  if (addr & 3)
+    abort ();
+
+  /* Search all cache blocks for one that is at this address.  */
+  db = dcache_valid.next;
+  while (db != &dcache_valid)
+    {
+      if ((addr & ~LINE_SIZE_MASK)== db->addr)
+       return db;
+      db = db->next;
+    }
+  return NULL;
+}
+
+/*  Return the int data at address ADDR in dcache block DC.  */
+static
+int
+dcache_value (db, addr)
+     struct dcache_block *db;
+     unsigned int addr;
+{
+  if (addr & 3)
+    abort ();
+  return (db->data[XFORM(addr)]);
+}
+
+/* Get a free cache block, put or keep it on the valid list,
+   and return its address.  The caller should store into the block
+   the address and data that it describes, then remque it from the
+   free list and insert it into the valid list.  This procedure
+   prevents errors from creeping in if a ninMemGet is interrupted
+   (which used to put garbage blocks in the valid list...).  */
+static
+struct dcache_block *
+dcache_alloc ()
+{
+  register struct dcache_block *db;
+
+  if ((db = dcache_free.next) == &dcache_free)
+    {
+      /* If we can't get one from the free list, take last valid and put
+        it on the free list.  */
+      db = dcache_valid.last;
+      remque (db);
+      insque (db, &dcache_free);
+    }
+
+  remque (db);
+  insque (db, &dcache_valid);
+  return (db);
+}
+
+/* Return the contents of the word at address ADDR in the remote machine,
+   using the data cache.  */
+static
+int
+dcache_fetch (addr)
+     CORE_ADDR addr;
+{
+  register struct dcache_block *db;
+
+  db = dcache_hit (addr);
+  if (db == 0)
+    {
+      db = dcache_alloc ();
+      immediate_quit++;
+      hms_read_inferior_memory(addr & ~LINE_SIZE_MASK, (unsigned char *)db->data, LINE_SIZE);
+      immediate_quit--;
+      db->addr = addr & ~LINE_SIZE_MASK;
+      remque (db);                     /* Off the free list */
+      insque (db, &dcache_valid);      /* On the valid list */
+    }
+  return (dcache_value (db, addr));
+}
+
+/* Write the word at ADDR both in the data cache and in the remote machine.  */
+static void
+dcache_poke (addr, data)
+     CORE_ADDR addr;
+     int data;
+{
+  register struct dcache_block *db;
+
+  /* First make sure the word is IN the cache.  DB is its cache block.  */
+  db = dcache_hit (addr);
+  if (db == 0)
+  {
+    db = dcache_alloc ();
+    immediate_quit++;
+    hms_write_inferior_memory(addr & ~LINE_SIZE_MASK, (unsigned char *)db->data, LINE_SIZE);
+    immediate_quit--;
+    db->addr = addr & ~LINE_SIZE_MASK;
+    remque (db);               /* Off the free list */
+    insque (db, &dcache_valid);        /* On the valid list */
+  }
+
+  /* Modify the word in the cache.  */
+  db->data[XFORM(addr)] = data;
+
+  /* Send the changed word.  */
+  immediate_quit++;
+  hms_write_inferior_memory(addr, (unsigned char *)&data, 4);
+  immediate_quit--;
+}
+
+/* The cache itself. */
+struct dcache_block the_cache[DCACHE_SIZE];
+
+/* Initialize the data cache.  */
+static void
+dcache_init ()
+{
+  register i;
+  register struct dcache_block *db;
+
+  db = the_cache;
+  dcache_free.next = dcache_free.last = &dcache_free;
+  dcache_valid.next = dcache_valid.last = &dcache_valid;
+  for (i=0;i<DCACHE_SIZE;i++,db++)
+    insque (db, &dcache_free);
+}
 
-static int timeout = 5;
+
+/***********************************************************************
+ * I/O stuff stolen from remote-eb.c
+ ***********************************************************************/
+
+static int timeout = 2;
 static char *dev_name  = "/dev/ttya";
 
 
-static int quiet;
+
 
 /* Descriptor for I/O to remote machine.  Initialize it to -1 so that
    hms_open knows that we don't have a file open when the program
@@ -79,6 +254,8 @@ int hms_desc = -1;
 #define OPEN(x) ((x) >= 0)
 
 
+void hms_open();
+
 #define ON     1
 #define OFF    0
 static void
@@ -109,25 +286,41 @@ int       turnon;
   ioctl (desc, TIOCSETP, &sg);
 }
 
-/* Suck up all the input from the hms */
-slurp_input()
+
+/* Read a character from the remote system, doing all the fancy
+   timeout stuff.  */
+static int
+readchar ()
 {
-  char buf[8];
+  char buf;
 
+  buf = '\0';
 #ifdef HAVE_TERMIO
   /* termio does the timeout for us.  */
-  while (read (hms_desc, buf, 8) > 0);
+  read (hms_desc, &buf, 1);
 #else
   alarm (timeout);
-  while (read (hms_desc, buf, 8) > 0);
+  if (read (hms_desc, &buf, 1) < 0)
+  {
+    if (errno == EINTR)
+     error ("Timeout reading from remote system.");
+    else
+     perror_with_name ("remote");
+  }
   alarm (0);
 #endif
+
+  if (buf == '\0')
+   error ("Timeout reading from remote system.");
+
+  if (!quiet)
+   printf("%c",buf);
+  
+  return buf & 0x7f;
 }
 
-/* Read a character from the remote system, doing all the fancy
-   timeout stuff.  */
 static int
-readchar ()
+readchar_nofail ()
 {
   char buf;
 
@@ -138,21 +331,16 @@ readchar ()
 #else
   alarm (timeout);
   if (read (hms_desc, &buf, 1) < 0)
-    {
-      if (errno == EINTR)
-       error ("Timeout reading from remote system.");
-      else
-       perror_with_name ("remote");
-    }
+  {
+    return 0;
+  }
   alarm (0);
 #endif
 
-  if (buf == '\0')
-    error ("Timeout reading from remote system.");
-
-if (!quiet)
-  printf("'%c'",buf);
-  
+  if (buf == '\0') 
+  {
+    return 0;
+  }
   return buf & 0x7f;
 }
 
@@ -267,16 +455,10 @@ volatile int n_alarms;
 void
 hms_timer ()
 {
-#if 0
-  if (kiodebug)
-    printf ("hms_timer called\n");
-#endif
   n_alarms++;
 }
 #endif
 
-/* malloc'd name of the program on the remote system.  */
-static char *prog_name = NULL;
 
 /* Number of SIGTRAPs we need to simulate.  That is, the next
    NEED_ARTIFICIAL_TRAP calls to hms_wait should just return
@@ -289,15 +471,16 @@ hms_kill(arg,from_tty)
 char   *arg;
 int    from_tty;
 {
-#if 0
-       DENTER("hms_kill()");
-       fprintf (hms_stream, "K");
 
-       fprintf (hms_stream, "\r");
-       expect_prompt ();
-       DEXIT("hms_kill()");
-#endif
 }
+
+static check_open()
+{
+  if (!OPEN(hms_desc)) {
+      hms_open("",0);
+    }  
+}
+
 /*
  * Download a file specified in 'args', to the hms. 
  */
@@ -312,15 +495,14 @@ int       fromtty;
   char buffer[1024];
        
   DENTER("hms_load()");
-  if (!OPEN(hms_desc))
-  {
-    printf_filtered("HMS not open. Use 'target' command to open HMS\n");
-    return;
-  }
+  check_open();
+
+  dcache_flush();
+  inferior_pid = 0;  
   abfd = bfd_openr(args,"coff-h8300");
   if (!abfd) 
   {
-    printf_filtered("Can't open a bfd on file\n");
+    printf_filtered("Unable to open file %s\n", args);
     return;
   }
 
@@ -366,7 +548,8 @@ hms_create_inferior (execfile, args, env)
    error ("No exec file specified");
 
   entry_pt = (int) bfd_get_start_address (exec_bfd);
-
+  check_open();
+  
   if (OPEN(hms_desc))
   {
     
@@ -376,28 +559,17 @@ hms_create_inferior (execfile, args, env)
     /* Clear the input because what the hms sends back is different
      * depending on whether it was running or not.
      */
-    /* slurp_input();  /* After this there should be a prompt */
+
     hms_write_cr("r");
        
     expect_prompt();
-    printf_filtered("Do you want to download '%s' (y/n)? [y] : ",prog_name);
-  {    
-    char buffer[10];
-    gets(buffer);
-    if (*buffer != 'n') {
-       hms_load(prog_name,0);
-      }
-  }
 
 
     insert_breakpoints ();     /* Needed to get correct instruction in cache */
     proceed(entry_pt, -1, 0);
 
 
-  } else 
-  {
-    printf_filtered("Hms not open yet.\n");
-  }
+  } 
   DEXIT("hms_create_inferior()");
 }
 
@@ -412,22 +584,12 @@ hms_create_inferior (execfile, args, env)
 #endif
 
 static struct {int rate, damn_b;} baudtab[] = {
-       {0, B0},
-       {50, B50},
-       {75, B75},
-       {110, B110},
-       {134, B134},
-       {150, B150},
-       {200, B200},
+       {9600, B9600},
+       {19200, B19200},
        {300, B300},
-       {600, B600},
        {1200, B1200},
-       {1800, B1800},
        {2400, B2400},
        {4800, B4800},
-       {9600, B9600},
-       {19200, B19200},
-       {38400, B38400},
        {-1, -1},
 };
 
@@ -438,7 +600,7 @@ static int damn_b (rate)
 
   for (i = 0; baudtab[i].rate != -1; i++)
     if (rate == baudtab[i].rate) return baudtab[i].damn_b;
-  return B38400;       /* Random */
+  return B19200;
 }
 
 
@@ -485,12 +647,78 @@ char **p;
 }
 
 static int baudrate = 9600;
+
+static int
+is_baudrate_right()
+{
+  
+
+  /* Put this port into NORMAL mode, send the 'normal' character */
+  hms_write("\001", 1);                /* Control A */
+  hms_write("\r", 1);          /* Cr */
+
+  while ( readchar_nofail()) /* Skip noise we put there */
+   ;
+  
+  hms_write("r");
+  if (readchar_nofail() == 'r')  
+   return 1;
+
+  /* Not the right baudrate, or the board's not on */
+  return 0;
+  
+
+}
+static void
+set_rate()
+{
+  TERMINAL sg;    
+  ioctl (hms_desc, TIOCGETP, &sg);
+#ifdef HAVE_TERMIO
+  sg.c_cc[VMIN] = 0;           /* read with timeout.  */
+  sg.c_cc[VTIME] = timeout * 10;
+  sg.c_lflag &= ~(ICANON | ECHO);
+  sg.c_cflag = (sg.c_cflag & ~CBAUD) | damn_b (baudrate);
+#else
+  sg.sg_ispeed = damn_b (baudrate);
+  sg.sg_ospeed = damn_b (baudrate);
+  sg.sg_flags |= RAW | ANYP;
+  sg.sg_flags &= ~ECHO;
+#endif
+
+  ioctl (hms_desc, TIOCSETP, &sg);
+}
+
+static void
+get_baudrate_right()
+{
+
+  int which_rate = 0;
+  
+  while (!is_baudrate_right()) 
+  {
+    if (baudtab[which_rate].rate == -1)
+    {
+      which_rate = 0;
+    }
+    else
+    {
+      which_rate++;
+    }
+    
+    baudrate = baudtab[which_rate].rate;
+    printf_filtered("Board not responding, trying %d baud\n",baudrate);
+    QUIT;
+    set_rate();
+  }
+}
+
 static void
 hms_open (name, from_tty)
      char *name;
      int from_tty;
 {
-  TERMINAL sg;
+
   unsigned int prl;
   char *p;
   
@@ -501,32 +729,17 @@ hms_open (name, from_tty)
     
   }
   
-  printf("Input string %s\n", name);
-  
-  prog_name = get_word(&name);
-  
   hms_close (0);
 
   hms_desc = open (dev_name, O_RDWR);
   if (hms_desc < 0)
    perror_with_name (dev_name);
-  ioctl (hms_desc, TIOCGETP, &sg);
-#ifdef HAVE_TERMIO
-  sg.c_cc[VMIN] = 0;           /* read with timeout.  */
-  sg.c_cc[VTIME] = timeout * 10;
-  sg.c_lflag &= ~(ICANON | ECHO);
-  sg.c_cflag = (sg.c_cflag & ~CBAUD) | damn_b (baudrate);
-#else
-  sg.sg_ispeed = damn_b (baudrate);
-  sg.sg_ospeed = damn_b (baudrate);
-  sg.sg_flags |= RAW | ANYP;
-  sg.sg_flags &= ~ECHO;
-#endif
 
-  ioctl (hms_desc, TIOCSETP, &sg);
+  set_rate();
+
+  dcache_init();
 
 
-  push_target (&hms_ops);
   /* start_remote ();              /* Initialize gdb process mechanisms */
 
 
@@ -543,11 +756,7 @@ hms_open (name, from_tty)
    perror ("hms_open: error in signal");
 #endif
 
-
-  /* Put this port into NORMAL mode, send the 'normal' character */
-  hms_write("\001", 1);                /* Control A */
-  hms_write("\r", 1);          /* Cr */
-  expect_prompt ();
+  get_baudrate_right();
   
   /* Hello?  Are you there?  */
   write (hms_desc, "\r", 1);
@@ -558,7 +767,7 @@ hms_open (name, from_tty)
   hms_clear_breakpoints();
 
 
-  printf_filtered("Remote debugging on an H8/300 HMS via %s %s.\n",dev_name,prog_name);
+  printf_filtered("Remote debugging on an H8/300 HMS via %s.\n",dev_name);
 
   DEXIT("hms_open()");
 }
@@ -603,8 +812,6 @@ hms_attach (args, from_tty)
 {
 
   DENTER("hms_attach()");
-  if (from_tty)
-      printf_filtered ("Attaching to remote program %s.\n", prog_name);
 
   /* push_target(&hms_ops);    /* This done in hms_open() */
 
@@ -655,6 +862,8 @@ hms_resume (step, sig)
      int step, sig;
 {
   DENTER("hms_resume()");
+  dcache_flush();
+  
   if (step)    
   {
     hms_write_cr("s");
@@ -686,7 +895,7 @@ hms_wait (status)
      of the string cannot recur in the string, or we will not
      find some cases of the string in the input.  */
   
-  static char bpt[] = "At breakpoint:";
+  static char bpt[] = "At breakpoint:\r";
   /* It would be tempting to look for "\n[__exit + 0x8]\n"
      but that requires loading symbols with "yc i" and even if
      we did do that we don't know that the file has symbols.  */
@@ -703,43 +912,44 @@ hms_wait (status)
   int ch_handled;
   int old_timeout = timeout;
   int old_immediate_quit = immediate_quit;
-
+  int swallowed_cr = 0;
+  
   DENTER("hms_wait()");
 
   WSETEXIT ((*status), 0);
 
   if (need_artificial_trap != 0)
-    {
-      WSETSTOP ((*status), SIGTRAP);
-      need_artificial_trap--;
-      return 0;
-    }
+  {
+    WSETSTOP ((*status), SIGTRAP);
+    need_artificial_trap--;
+    return 0;
+  }
 
-  timeout = 0;         /* Don't time out -- user program is running. */
-  immediate_quit = 1;  /* Helps ability to QUIT */
+  timeout = 0;                 /* Don't time out -- user program is running. */
+  immediate_quit = 1;          /* Helps ability to QUIT */
   while (1) {
-      QUIT;            /* Let user quit and leave process running */
+      QUIT;                    /* Let user quit and leave process running */
       ch_handled = 0;
       ch = readchar ();
       if (ch == *bp) {
          bp++;
          if (*bp == '\0')
-           break;
+          break;
          ch_handled = 1;
 
          *swallowed_p++ = ch;
-      } else
-       bp = bpt;
+       } else
+        bp = bpt;
       if (ch == *ep || *ep == '?') {
          ep++;
          if (*ep == '\0')
-           break;
+          break;
 
          if (!ch_handled)
-           *swallowed_p++ = ch;
+          *swallowed_p++ = ch;
          ch_handled = 1;
-      }, sal.line);
-d979 3
+       } else
+        ep = exitmsg;
       if (!ch_handled) {
          char *p;
          /* Print out any characters which have been swallowed.  */
@@ -769,9 +979,6 @@ d979 3
   
   timeout = old_timeout;
   immediate_quit = old_immediate_quit;
-       printf ("%s is at %s:%d.\n",
-               local_hex_string(sal.pc), 
-               sal.symtab->filename, sal.line);
   DEXIT("hms_wait()");
   return 0;
 }
@@ -851,15 +1058,15 @@ if (!quiet)
   }
 }
 
-           printf ("Line %d of \"%s\" is at pc %s but contains no code.\n",
-                   sal.line, sal.symtab->filename, local_hex_string(start_pc));
+hms_write_cr(s)
+char *s;
 {
 hms_write( s, strlen(s));
-             printf ("Line %d of \"%s\" starts at pc %s",
-                     sal.line, sal.symtab->filename, 
-                     local_hex_string(start_pc));
-             printf (" and ends at %s.\n",
-                     local_hex_string(end_pc));
+hms_write("\r",1);  
+}
+
+static void
+hms_fetch_registers ()
 {
 #define REGREPLY_SIZE 79
   char linebuf[REGREPLY_SIZE+1];
@@ -867,8 +1074,8 @@ hms_write( s, strlen(s));
   int s ;
   int gottok;
   
-       printf ("Line number %d is out of range for \"%s\".\n",
-               sal.line, sal.symtab->filename);
+  REGISTER_TYPE reg[NUM_REGS];
+  int foo[8];
   check_open();
   
   do 
@@ -942,7 +1149,7 @@ hms_store_register (regno)
      int regno;
 {
 
-  printf ("Expression not found\n");
+  /* printf("hms_store_register() called.\n"); fflush(stdout); /* */
   if (regno == -1)
    hms_store_registers ();
   else
@@ -1020,7 +1227,7 @@ hms_xfer_inferior_memory(memaddr, myaddr, len, write, target)
   addr = memaddr & - sizeof (int);
   count   = (((memaddr + len) - addr) + sizeof (int) - 1) / sizeof (int);
 
-  printf ("Expression not found\n");
+
   buffer = (int *)alloca (count * sizeof (int));
   if (write)
   {
index 1409dcc9bff7076f1c5e8f62dc06aa11898ae276..330576eae26d8e4bae23d3dcda8866396e007ec7 100644 (file)
@@ -19,7 +19,31 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.  */
 
 /* Contributed by Steve Chamberlain sac@cygnus.com */
 
-#define IEEE_FLOAT 1
+
+#define UNSIGNED_SHORT(X) ((X) & 0xffff)
+
+
+#define EXTRA_FRAME_INFO       \
+       struct frame_saved_regs *fsr;   \
+       CORE_ADDR from_pc; \
+       CORE_ADDR args_pointer;\
+        CORE_ADDR locals_pointer ;
+
+
+
+/* Zero the frame_saved_regs pointer when the frame is initialized,
+   so that FRAME_FIND_SAVED_REGS () will know to allocate and
+   initialize a frame_saved_regs struct the first time it is called.
+   Set the arg_pointer to -1, which is not valid; 0 and other values
+   indicate real, cached values.  */
+
+#define INIT_EXTRA_FRAME_INFO(fromleaf, fi) \
+       init_extra_frame_info (fromleaf, fi)
+
+extern void init_extra_frame_info ();
+
+
+#define IEEE_FLOAT
 
 /* Define the bit, byte, and word ordering of the machine.  */
 #define TARGET_BYTE_ORDER BIG_ENDIAN
@@ -46,7 +70,7 @@ extern CORE_ADDR h8300_skip_prologue ();
    some instructions.  */
 
 #define SAVED_PC_AFTER_CALL(frame) \
-read_memory_integer (read_register (SP_REGNUM), 2)
+UNSIGNED_SHORT(read_memory_integer (read_register (SP_REGNUM), 2))
 
 /* Stack grows downward.  */
 
@@ -69,7 +93,7 @@ read_memory_integer (read_register (SP_REGNUM), 2)
    define this before including this file.  */
 
 
-#define DECR_PC_AFTER_BREAK 2
+#define DECR_PC_AFTER_BREAK 0
 
 
 /* Nonzero if instruction at PC is a return instruction.  */
@@ -157,19 +181,15 @@ read_memory_integer (read_register (SP_REGNUM), 2)
 /* Store the address of the place in which to copy the structure the
    subroutine will return.  This is called from call_function. */
 
-#define STORE_STRUCT_RETURN(ADDR, SP) \
-  { write_register (0, (ADDR)); abort(); }
+/*#define STORE_STRUCT_RETURN(ADDR, SP) \
+  { write_register (0, (ADDR)); abort(); }*/
 
 /* Extract from an array REGBUF containing the (raw) register state
    a function return value of type TYPE, and copy that, in virtual format,
-   into VALBUF.  This is assuming that floating point values are returned
-   as doubles in d0/d1.  */
-
+   into VALBUF.  */
 
 #define EXTRACT_RETURN_VALUE(TYPE,REGBUF,VALBUF) \
-  bcopy ((char *)(REGBUF) +                                            \
-                (TYPE_LENGTH(TYPE) >= 4 ? 0 : 4 - TYPE_LENGTH(TYPE)),  \
-        VALBUF, TYPE_LENGTH(TYPE))
+  bcopy ((char *)(REGBUF), VALBUF, TYPE_LENGTH(TYPE))
 
 
 /* Write into appropriate registers a function return value
@@ -220,11 +240,22 @@ read_memory_integer (read_register (SP_REGNUM), 2)
 #define FRAMELESS_FUNCTION_INVOCATION(FI, FRAMELESS) \
   (FRAMELESS) = frameless_look_for_prologue(FI)
 
-#define FRAME_SAVED_PC(FRAME) (read_memory_integer ((FRAME)->frame + 2, 2))
+/* Any function with a frame looks like this
+   SECOND ARG
+   FIRST ARG
+   RET PC
+   SAVED R2
+   SAVED R3
+   SAVED FP   <-FP POINTS HERE
+   LOCALS0
+   LOCALS1    <-SP POINTS HERE
+   
+   */
+#define FRAME_SAVED_PC(FRAME) frame_saved_pc(FRAME)
 
-#define FRAME_ARGS_ADDRESS(fi) ((fi)->frame)
+#define FRAME_ARGS_ADDRESS(fi) frame_args_address(fi)
 
-#define FRAME_LOCALS_ADDRESS(fi) ((fi)->frame)
+#define FRAME_LOCALS_ADDRESS(fi) frame_locals_address(fi);
 
 /* Set VAL to the number of args passed to frame described by FI.
    Can set VAL to -1, meaning no way to tell.  */
@@ -237,7 +268,7 @@ read_memory_integer (read_register (SP_REGNUM), 2)
 
 /* Return number of bytes at start of arglist that are not really args.  */
 
-#define FRAME_ARGS_SKIP 4
+#define FRAME_ARGS_SKIP 0
 
 /* Put here the code to store, into a struct frame_saved_regs,
    the addresses of the saved registers of frame described by FRAME_INFO.
@@ -245,12 +276,13 @@ read_memory_integer (read_register (SP_REGNUM), 2)
    ways in the stack frame.  sp is even more special:
    the address we return for it IS the sp for the next frame.  */
 
-#define FRAME_FIND_SAVED_REGS(frame_info, frame_saved_regs)          abort();
+#define FRAME_FIND_SAVED_REGS(frame_info, frame_saved_regs)        \
+   frame_find_saved_regs(frame_info, &(frame_saved_regs))
 \f
 
 /* Push an empty stack frame, to record the current PC, etc.  */
 
-#define PUSH_DUMMY_FRAME       { h8300_push_dummy_frame (); }
+/*#define PUSH_DUMMY_FRAME     { h8300_push_dummy_frame (); }*/
 
 /* Discard from the stack the innermost frame, restoring all registers.  */
 
@@ -259,11 +291,16 @@ read_memory_integer (read_register (SP_REGNUM), 2)
 #define SHORT_INT_MAX 32767
 #define SHORT_INT_MIN -32768
 
-#undef longest_to_int
-#define longest_to_int(x) (x & 0xffff)
-
 
 #define REGISTER_CONVERT_TO_VIRTUAL(REGNUM,FROM,TO) \
 { bcopy ((FROM), (TO), 2); }
 #define REGISTER_CONVERT_TO_RAW(REGNUM,FROM,TO)        \
 { bcopy ((FROM), (TO), 4); }
+
+#define        BEFORE_MAIN_LOOP_HOOK   \
+  hms_before_main_loop();
+
+
+#define NAMES_HAVE_UNDERSCORE
+
+typedef unsigned short INSN_WORD;
index 2c8143de3b9d6f75d7d8336c03056833814b31e1..e3c31876aa286a9876e5e68703c32f0264fe1508 100644 (file)
@@ -690,13 +690,20 @@ unpack_long (type, valaddr)
   else if (code == TYPE_CODE_PTR
           || code == TYPE_CODE_REF)
     {
-      if (len == sizeof (CORE_ADDR))
-       {
-         CORE_ADDR retval;
-         bcopy (valaddr, &retval, sizeof (retval));
-         SWAP_TARGET_AND_HOST (&retval, sizeof (retval));
-         return retval;
-       }
+      if (len == sizeof(long))
+      {
+       long retval;
+       bcopy (valaddr, &retval, sizeof(retval));
+       SWAP_TARGET_AND_HOST (&retval, sizeof(retval));
+       return retval;
+      }
+      else if (len == sizeof(short))
+      {
+       short retval;
+       bcopy (valaddr, &retval, len);
+       SWAP_TARGET_AND_HOST (&retval, len);
+       return retval;
+      }
     }
   else if (code == TYPE_CODE_MEMBER)
     error ("not implemented: member types in unpack_long");