hppa native support
authorK. Richard Pixley <rich@cygnus>
Wed, 21 Oct 1992 04:57:35 +0000 (04:57 +0000)
committerK. Richard Pixley <rich@cygnus>
Wed, 21 Oct 1992 04:57:35 +0000 (04:57 +0000)
16 files changed:
gdb/.Sanitize
gdb/ChangeLog
gdb/Makefile.in
gdb/config/hppabsd.mh
gdb/config/hppabsd.mt
gdb/config/hppahpux.mh
gdb/config/hppahpux.mt
gdb/doc/gdbint.texinfo
gdb/hppab-nat.c [new file with mode: 0644]
gdb/hppab-tdep.c
gdb/hppah-nat.c [new file with mode: 0644]
gdb/hppah-tdep.c
gdb/nm-hppab.h [new file with mode: 0644]
gdb/nm-hppah.h [new file with mode: 0644]
gdb/xm-hppab.h
gdb/xm-hppah.h

index 6025169d092dbff659765cd6d5ea6ca065c949a8..3079abda06346735854bb656afc4f3ecbbe00a4f 100644 (file)
@@ -98,10 +98,10 @@ h8300-tdep.c
 hp300ux-xdep.c
 hppa-pinsn.c
 hppab-core.c
+hppab-nat.c
 hppab-tdep.c
-hppab-xdep.c
+hppah-nat.c
 hppah-tdep.c
-hppah-xdep.c
 i386-pinsn.c
 i386-stub.c
 i386-tdep.c
@@ -145,6 +145,8 @@ news-xdep.c
 nindy-share
 nindy-tdep.c
 nm-delta88.h
+nm-hppab.h
+nm-hppah.h
 nm-i386bsd.h
 nm-i386mach.h
 nm-i386v.h
index a6a983bdd25ba9387aa59b5e9db509c84bb0b446..e8fdb1b114db59eca2502f124c8469e2706b3d38 100644 (file)
@@ -1,3 +1,19 @@
+Tue Oct 20 21:32:18 1992  K. Richard Pixley  (rich@sendai.cygnus.com)
+
+       hppa native support (untested).
+
+       * config/hppahpux.mh, config/hppabsd.mh (XDEPFILES): now empty.
+         (NAT_FILE, NATDEPFILES): new macros.
+       * config/hppabsd.mt (TDEPFILES): removed exec.o and hppab-core.o.
+       * config/hppahpux.mt (TDEPFILES): removed exec.o.
+       * xm-hppa[bh].h (REGISTER_U_ADDR, U_REGS_OFFSET): removed.
+       * nm-hppa[bh].h, hppa[bh]-nat.c: new files.
+       * hppa[bh]-xdep.c: removed.
+       * hppa[bh]h-tdep.c: do not include ptrace.h.
+       * Makefile.in (HFILES): added nm-hppa[bh].h.
+
+       * doc/gdbint.texinfo: add PUSH_DUMMY_FRAME, POP_FRAME.
+
 Tue Oct 20 00:01:46 1992  Stu Grossman  (grossman at cygnus.com)
 
        * mips-nat.c:  Straighten out include files.  Work around
index b514f7e49f4e1df6dcdce89566682188829ac08d..a4f15ccd395497819ca9b973ab054d8dac99e2a1 100644 (file)
@@ -255,7 +255,8 @@ HFILES=     breakpoint.h buildsym.h call-cmds.h command.h defs.h \
        xm-m68k.h xm-sparc.h xm-sysv4.h xm-vax.h \
        nm-i386bsd.h nm-i386mach.h nm-i386v.h nm-i386v4.h nm-irix3.h \
        nm-irix4.h nm-linux.h nm-m88k.h nm-mips.h nm-news.h nm-rs6000.h \
-       nm-sun2.h nm-sun3.h nm-sun386.h nm-sun4os4.h nm-trash.h nm-ultra3.h
+       nm-sun2.h nm-sun3.h nm-sun386.h nm-sun4os4.h nm-trash.h \
+       nm-ultra3.h nm-hppab.h nm-hppah.h
 
 REMOTE_EXAMPLES = m68k-stub.c i386-stub.c sparc-stub.c rem-multi.shar
 
index 701af04cd654423f2d19456275008201c6f7363d..2efde1ac5ddc9db10040fb57261fa84ae7739790 100644 (file)
@@ -1,3 +1,5 @@
 # Host: Hewlett-Packard PA-RISC machine, running BSD
-XDEPFILES= hppab-xdep.o coredep.o corelow.o
+XDEPFILES= 
 XM_FILE= xm-hppab.h
+NAT_FILE= nm-hppab.h
+NATDEPFILES= hppab-nat.o coredep.o corelow.o exec.o hppab-core.o
index a0aa1f2e3837a91ceab18882b1eed1ed90f9e2ad..1260ab70df274c1399274c956c52bdb211ec82b6 100644 (file)
@@ -1,4 +1,4 @@
 # TARGET: HP PA-RISC running bsd
-TDEPFILES= hppa-pinsn.o hppab-tdep.o exec.o hppab-core.o
+TDEPFILES= hppa-pinsn.o hppab-tdep.o
 TM_FILE= tm-hppab.h
 
index 4d203a20bb1de890590f482c0513f977b5e305c7..96b0b1551b240df22901f376159120c16b72dff2 100644 (file)
@@ -1,6 +1,8 @@
 # Host: Hewlett-Packard PA-RISC machine, running HPUX 
 TERMCAP = -lcurses
-XDEPFILES= hppah-xdep.o coredep.o corelow.o
+XDEPFILES= 
 XM_FILE= xm-hppah.h
+NAT_FILE= nm-hppah.h
+NATDEPFILES= exec.o coredep.o corelow.o
 REGEX=regex.o
 REGEX1=regex.o
index 08501083ee91433a122b058a188ee4b33d62810b..b8f2f8f76d7bafe655d699080cd457e4a5f226ea 100644 (file)
@@ -1,3 +1,3 @@
 # TARGET: HP PA-RISC running hpux
-TDEPFILES= hppa-pinsn.o hppah-tdep.o exec.o
+TDEPFILES= hppa-pinsn.o hppah-tdep.o
 TM_FILE= tm-hppah.h
index 63e1a056afe3112fff6e04707eb27b8dd7089772..c3188b0fc49844652e4dc055b1e827d8650f9f95 100644 (file)
@@ -1582,6 +1582,10 @@ system.  These macros and their meanings are:
 Eliminate host conditionals from this list as they are identified.}
 
 @table @code
+@item PUSH_DUMMY_FRAME
+Used in @samp{call_function_by_hand} to create an artificial stack frame.
+@item POP_FRAME
+Used in @samp{call_function_by_hand} to remove an artificial stack frame.
 @item ALIGN_SIZE
 alloca.c
 @item BLOCK_ADDRESS_FUNCTION_RELATIVE
diff --git a/gdb/hppab-nat.c b/gdb/hppab-nat.c
new file mode 100644 (file)
index 0000000..752b370
--- /dev/null
@@ -0,0 +1,395 @@
+/* Machine-dependent hooks for the unix child process stratum.  This
+   code is for the HP PA-RISC cpu.
+
+   Copyright 1986, 1987, 1989, 1990, 1991, 1992 Free Software Foundation, Inc.
+
+   Contributed by the Center for Software Science at the
+   University of Utah (pa-gdb-bugs@cs.utah.edu).
+
+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.  */
+
+#include "defs.h"
+#include "inferior.h"
+
+#ifndef PT_ATTACH
+#define PT_ATTACH PTRACE_ATTACH
+#endif
+#ifndef PT_DETACH
+#define PT_DETACH PTRACE_DETACH
+#endif
+
+/* This function simply calls ptrace with the given arguments.  
+   It exists so that all calls to ptrace are isolated in this 
+   machine-dependent file. */
+#ifdef WANT_NATIVE_TARGET
+int
+call_ptrace (request, pid, addr, data)
+     int request, pid;
+     PTRACE_ARG3_TYPE addr;
+     int data;
+{
+  return ptrace (request, pid, addr, data);
+}
+#endif /* WANT_NATIVE_TARGET */
+
+#ifdef DEBUG_PTRACE
+/* For the rest of the file, use an extra level of indirection */
+/* This lets us breakpoint usefully on call_ptrace. */
+#define ptrace call_ptrace
+#endif
+
+void
+kill_inferior ()
+{
+  if (inferior_pid == 0)
+    return;
+  ptrace (PT_KILL, inferior_pid, (PTRACE_ARG3_TYPE) 0, 0);
+  wait ((int *)0);
+  target_mourn_inferior ();
+}
+
+#ifdef ATTACH_DETACH
+/* Nonzero if we are debugging an attached process rather than
+   an inferior.  */
+extern int attach_flag;
+
+/* Start debugging the process whose number is PID.  */
+int
+attach (pid)
+     int pid;
+{
+  errno = 0;
+  ptrace (PT_ATTACH, pid, (PTRACE_ARG3_TYPE) 0, 0);
+  if (errno)
+    perror_with_name ("ptrace");
+  attach_flag = 1;
+  return pid;
+}
+
+/* Stop debugging the process whose number is PID
+   and continue it with signal number SIGNAL.
+   SIGNAL = 0 means just continue it.  */
+
+void
+detach (signal)
+     int signal;
+{
+  errno = 0;
+  ptrace (PT_DETACH, inferior_pid, (PTRACE_ARG3_TYPE) 1, signal);
+  if (errno)
+    perror_with_name ("ptrace");
+  attach_flag = 0;
+}
+#endif /* ATTACH_DETACH */
+\f
+
+
+#if !defined (FETCH_INFERIOR_REGISTERS)
+
+/* KERNEL_U_ADDR is the amount to subtract from u.u_ar0
+   to get the offset in the core file of the register values.  */
+#if defined (KERNEL_U_ADDR_BSD)
+/* Get kernel_u_addr using BSD-style nlist().  */
+CORE_ADDR kernel_u_addr;
+
+#include <a.out.gnu.h>         /* For struct nlist */
+
+void
+_initialize_kernel_u_addr ()
+{
+  struct nlist names[2];
+
+  names[0].n_un.n_name = "_u";
+  names[1].n_un.n_name = NULL;
+  if (nlist ("/vmunix", names) == 0)
+    kernel_u_addr = names[0].n_value;
+  else
+    fatal ("Unable to get kernel u area address.");
+}
+#endif /* KERNEL_U_ADDR_BSD.  */
+
+#if defined (KERNEL_U_ADDR_HPUX)
+/* Get kernel_u_addr using HPUX-style nlist().  */
+CORE_ADDR kernel_u_addr;
+
+struct hpnlist {      
+        char *          n_name;
+        long            n_value;  
+        unsigned char   n_type;   
+        unsigned char   n_length;  
+        short           n_almod;   
+        short           n_unused;
+};
+static struct hpnlist nl[] = {{ "_u", -1, }, { (char *) 0, }};
+
+/* read the value of the u area from the hp-ux kernel */
+void _initialize_kernel_u_addr ()
+{
+    struct user u;
+    nlist ("/hp-ux", &nl);
+    kernel_u_addr = nl[0].n_value;
+}
+#endif /* KERNEL_U_ADDR_HPUX.  */
+
+#if !defined (offsetof)
+#define offsetof(TYPE, MEMBER) ((unsigned long) &((TYPE *)0)->MEMBER)
+#endif
+
+/* U_REGS_OFFSET is the offset of the registers within the u area.  */
+#if !defined (U_REGS_OFFSET)
+#define U_REGS_OFFSET \
+  ptrace (PT_READ_U, inferior_pid, \
+          (PTRACE_ARG3_TYPE) (offsetof (struct user, u_ar0)), 0) \
+    - KERNEL_U_ADDR
+#endif
+
+/* Registers we shouldn't try to fetch.  */
+#if !defined (CANNOT_FETCH_REGISTER)
+#define CANNOT_FETCH_REGISTER(regno) 0
+#endif
+
+/* Fetch one register.  */
+
+static void
+fetch_register (regno)
+     int regno;
+{
+  register unsigned int regaddr;
+  char buf[MAX_REGISTER_RAW_SIZE];
+  char mess[128];                              /* For messages */
+  register int i;
+
+  /* Offset of registers within the u area.  */
+  unsigned int offset;
+
+  if (CANNOT_FETCH_REGISTER (regno))
+    {
+      bzero (buf, REGISTER_RAW_SIZE (regno));  /* Supply zeroes */
+      supply_register (regno, buf);
+      return;
+    }
+
+  offset = U_REGS_OFFSET;
+
+  regaddr = register_addr (regno, offset);
+  for (i = 0; i < REGISTER_RAW_SIZE (regno); i += sizeof (int))
+    {
+      errno = 0;
+      *(int *) &buf[i] = ptrace (PT_RUREGS, inferior_pid,
+                                (PTRACE_ARG3_TYPE) regaddr, 0);
+      regaddr += sizeof (int);
+      if (errno != 0)
+       {
+         sprintf (mess, "reading register %s (#%d)", reg_names[regno], regno);
+         perror_with_name (mess);
+       }
+    }
+  supply_register (regno, buf);
+}
+
+#endif /* !defined (FETCH_INFERIOR_REGISTERS).  */
+/* Fetch all registers, or just one, from the child process.  */
+
+#ifndef FETCH_INFERIOR_REGISTERS
+void
+fetch_inferior_registers (regno)
+     int regno;
+{
+  if (regno == -1)
+    for (regno = 0; regno < NUM_REGS; regno++)
+      fetch_register (regno);
+  else
+    fetch_register (regno);
+}
+
+/* Registers we shouldn't try to store.  */
+#if !defined (CANNOT_STORE_REGISTER)
+#define CANNOT_STORE_REGISTER(regno) 0
+#endif
+
+/* Store our register values back into the inferior.
+   If REGNO is -1, do this for all registers.
+   Otherwise, REGNO specifies which register (so we can save time).  */
+
+void
+store_inferior_registers (regno)
+     int regno;
+{
+  register unsigned int regaddr;
+  char buf[80];
+  extern char registers[];
+  register int i;
+
+  unsigned int offset = U_REGS_OFFSET;
+
+  if (regno >= 0)
+    {
+      regaddr = register_addr (regno, offset);
+      for (i = 0; i < REGISTER_RAW_SIZE (regno); i += sizeof(int))
+       {
+         errno = 0;
+         ptrace (PT_WRITE_U, inferior_pid, (PTRACE_ARG3_TYPE) regaddr,
+                 *(int *) &registers[REGISTER_BYTE (regno) + i]);
+         if (errno != 0)
+           {
+             sprintf (buf, "writing register number %d(%d)", regno, i);
+             perror_with_name (buf);
+           }
+         regaddr += sizeof(int);
+       }
+    }
+  else
+    {
+      for (regno = 0; regno < NUM_REGS; regno++)
+       {
+         if (CANNOT_STORE_REGISTER (regno))
+           continue;
+         regaddr = register_addr (regno, offset);
+         for (i = 0; i < REGISTER_RAW_SIZE (regno); i += sizeof(int))
+           {
+             errno = 0;
+             ptrace (PT_WRITE_U, inferior_pid, (PTRACE_ARG3_TYPE) regaddr,
+                     *(int *) &registers[REGISTER_BYTE (regno) + i]);
+             if (errno != 0)
+               {
+                 sprintf (buf, "writing register number %d(%d)", regno, i);
+                 perror_with_name (buf);
+               }
+             regaddr += sizeof(int);
+           }
+       }
+    }
+  return;
+}
+#endif /* !defined(FETCH_INFERIOR_REGISTERS) */
+
+/* Resume execution of the inferior process.
+   If STEP is nonzero, single-step it.
+   If SIGNAL is nonzero, give it that signal.  */
+
+void
+child_resume (step, signal)
+     int step;
+     int signal;
+{
+  errno = 0;
+
+  /* An address of (PTRACE_ARG3_TYPE) 1 tells ptrace to continue from where
+     it was. (If GDB wanted it to start some other way, we have already
+     written a new PC value to the child.)  */
+
+  if (step)
+    ptrace (PT_STEP, inferior_pid, (PTRACE_ARG3_TYPE) 1, signal);
+  else
+    ptrace (PT_CONTINUE, inferior_pid, (PTRACE_ARG3_TYPE) 1, signal);
+
+  if (errno)
+    perror_with_name ("ptrace");
+}
+
+/* NOTE! I tried using PTRACE_READDATA, etc., to read and write memory
+   in the NEW_SUN_PTRACE case.
+   It ought to be straightforward.  But it appears that writing did
+   not write the data that I specified.  I cannot understand where
+   it got the data that it actually did write.  */
+
+/* Copy LEN bytes to or from inferior's memory starting at MEMADDR
+   to debugger memory starting at MYADDR.   Copy to inferior if
+   WRITE is nonzero.
+  
+   Returns the length copied, which is either the LEN argument or zero.
+   This xfer function does not do partial moves, since child_ops
+   doesn't allow memory operations to cross below us in the target stack
+   anyway.  */
+
+int
+child_xfer_memory (memaddr, myaddr, len, write, target)
+     CORE_ADDR memaddr;
+     char *myaddr;
+     int len;
+     int write;
+     struct target_ops *target;                /* ignored */
+{
+  register int i;
+  /* Round starting address down to longword boundary.  */
+  register CORE_ADDR addr = memaddr & - sizeof (int);
+  /* Round ending address up; get number of longwords that makes.  */
+  register int count
+    = (((memaddr + len) - addr) + sizeof (int) - 1) / sizeof (int);
+  /* Allocate buffer of that many longwords.  */
+  register int *buffer = (int *) alloca (count * sizeof (int));
+
+  if (write)
+    {
+      /* Fill start and end extra bytes of buffer with existing memory data.  */
+
+      if (addr != memaddr || len < (int)sizeof (int)) {
+       /* Need part of initial word -- fetch it.  */
+        buffer[0] = ptrace (PT_READ_I, inferior_pid, (PTRACE_ARG3_TYPE) addr,
+                           0);
+      }
+
+      if (count > 1)           /* FIXME, avoid if even boundary */
+       {
+         buffer[count - 1]
+           = ptrace (PT_READ_I, inferior_pid,
+                     (PTRACE_ARG3_TYPE) (addr + (count - 1) * sizeof (int)),
+                     0);
+       }
+
+      /* Copy data to be written over corresponding part of buffer */
+
+      bcopy (myaddr, (char *) buffer + (memaddr & (sizeof (int) - 1)), len);
+
+      /* Write the entire buffer.  */
+
+      for (i = 0; i < count; i++, addr += sizeof (int))
+       {
+         errno = 0;
+         ptrace (PT_WRITE_D, inferior_pid, (PTRACE_ARG3_TYPE) addr,
+                 buffer[i]);
+         if (errno)
+           {
+             /* Using the appropriate one (I or D) is necessary for
+                Gould NP1, at least.  */
+             errno = 0;
+             ptrace (PT_WRITE_I, inferior_pid, (PTRACE_ARG3_TYPE) addr,
+                     buffer[i]);
+           }
+         if (errno)
+           return 0;
+       }
+    }
+  else
+    {
+      /* Read all the longwords */
+      for (i = 0; i < count; i++, addr += sizeof (int))
+       {
+         errno = 0;
+         buffer[i] = ptrace (PT_READ_I, inferior_pid,
+                             (PTRACE_ARG3_TYPE) addr, 0);
+         if (errno)
+           return 0;
+         QUIT;
+       }
+
+      /* Copy appropriate bytes out of the buffer.  */
+      bcopy ((char *) buffer + (memaddr & (sizeof (int) - 1)), myaddr, len);
+    }
+  return len;
+}
+
index 8fe6d289a8049a149f90a60869411af765f61e22..39d01cb8ed67bd899b4d2e15665fc9120f4bbc09 100644 (file)
@@ -50,7 +50,6 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.  */
 /*#include <sys/user.h>                After a.out.h  */
 #include <sys/file.h>
 #include <sys/stat.h>
-#include <sys/ptrace.h>
 #include <machine/psl.h>
 
 #ifdef KERNELDEBUG
diff --git a/gdb/hppah-nat.c b/gdb/hppah-nat.c
new file mode 100644 (file)
index 0000000..4a85fe1
--- /dev/null
@@ -0,0 +1,397 @@
+/* Machine-dependent hooks for the unix child process stratum.  This
+   code is for the HP PA-RISC cpu.
+
+   Copyright 1986, 1987, 1989, 1990, 1991, 1992 Free Software Foundation, Inc.
+
+   Contributed by the Center for Software Science at the
+   University of Utah (pa-gdb-bugs@cs.utah.edu).
+
+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.  */
+
+
+#include "defs.h"
+#include "inferior.h"
+
+#ifndef PT_ATTACH
+#define PT_ATTACH PTRACE_ATTACH
+#endif
+#ifndef PT_DETACH
+#define PT_DETACH PTRACE_DETACH
+#endif
+
+/* This function simply calls ptrace with the given arguments.  
+   It exists so that all calls to ptrace are isolated in this 
+   machine-dependent file. */
+#ifdef WANT_NATIVE_TARGET
+int
+call_ptrace (request, pid, addr, data)
+     int request, pid;
+     PTRACE_ARG3_TYPE addr;
+     int data;
+{
+  return ptrace (request, pid, addr, data, 0);
+}
+#endif /* WANT_NATIVE_TARGET */
+
+#ifdef DEBUG_PTRACE
+/* For the rest of the file, use an extra level of indirection */
+/* This lets us breakpoint usefully on call_ptrace. */
+#define ptrace call_ptrace
+#endif
+
+void
+kill_inferior ()
+{
+  if (inferior_pid == 0)
+    return;
+  ptrace (PT_EXIT, inferior_pid, (PTRACE_ARG3_TYPE) 0, 0, 0); /* PT_EXIT = PT_KILL ? */
+  wait ((int *)0);
+  target_mourn_inferior ();
+}
+
+#ifdef ATTACH_DETACH
+/* Nonzero if we are debugging an attached process rather than
+   an inferior.  */
+extern int attach_flag;
+
+/* Start debugging the process whose number is PID.  */
+int
+attach (pid)
+     int pid;
+{
+  errno = 0;
+  ptrace (PT_ATTACH, pid, (PTRACE_ARG3_TYPE) 0, 0, 0);
+  if (errno)
+    perror_with_name ("ptrace");
+  attach_flag = 1;
+  return pid;
+}
+
+/* Stop debugging the process whose number is PID
+   and continue it with signal number SIGNAL.
+   SIGNAL = 0 means just continue it.  */
+
+void
+detach (signal)
+     int signal;
+{
+  errno = 0;
+  ptrace (PT_DETACH, inferior_pid, (PTRACE_ARG3_TYPE) 1, signal, 0);
+  if (errno)
+    perror_with_name ("ptrace");
+  attach_flag = 0;
+}
+#endif /* ATTACH_DETACH */
+
+/* Fetch all registers, or just one, from the child process.  */
+
+void
+fetch_inferior_registers (regno)
+     int regno;
+{
+  if (regno == -1)
+    for (regno = 0; regno < NUM_REGS; regno++)
+      fetch_register (regno);
+  else
+    fetch_register (regno);
+}
+
+/* Registers we shouldn't try to store.  */
+#if !defined (CANNOT_STORE_REGISTER)
+#define CANNOT_STORE_REGISTER(regno) 0
+#endif
+
+/* Store our register values back into the inferior.
+   If REGNO is -1, do this for all registers.
+   Otherwise, REGNO specifies which register (so we can save time).  */
+
+void
+store_inferior_registers (regno)
+     int regno;
+{
+  register unsigned int regaddr;
+  char buf[80];
+  extern char registers[];
+  register int i;
+
+  unsigned int offset = U_REGS_OFFSET;
+
+  if (regno >= 0)
+    {
+      regaddr = register_addr (regno, offset);
+      for (i = 0; i < REGISTER_RAW_SIZE (regno); i += sizeof(int))
+       {
+         errno = 0;
+         ptrace (PT_WUAREA, inferior_pid, (PTRACE_ARG3_TYPE) regaddr,
+                 *(int *) &registers[REGISTER_BYTE (regno) + i], 0);
+         if (errno != 0)
+           {
+             sprintf (buf, "writing register number %d(%d)", regno, i);
+             perror_with_name (buf);
+           }
+         regaddr += sizeof(int);
+       }
+    }
+  else
+    {
+      for (regno = 0; regno < NUM_REGS; regno++)
+       {
+         if (CANNOT_STORE_REGISTER (regno))
+           continue;
+         regaddr = register_addr (regno, offset);
+         for (i = 0; i < REGISTER_RAW_SIZE (regno); i += sizeof(int))
+           {
+             errno = 0;
+             ptrace (PT_WUAREA, inferior_pid, (PTRACE_ARG3_TYPE) regaddr,
+                     *(int *) &registers[REGISTER_BYTE (regno) + i], 0);
+             if (errno != 0)
+               {
+                 sprintf (buf, "writing register number %d(%d)", regno, i);
+                 perror_with_name (buf);
+               }
+             regaddr += sizeof(int);
+           }
+       }
+    }
+  return;
+}
+
+/* KERNEL_U_ADDR is the amount to subtract from u.u_ar0
+   to get the offset in the core file of the register values.  */
+#if defined (KERNEL_U_ADDR_BSD)
+/* Get kernel_u_addr using BSD-style nlist().  */
+CORE_ADDR kernel_u_addr;
+
+#include <a.out.gnu.h>         /* For struct nlist */
+
+void
+_initialize_kernel_u_addr ()
+{
+  struct nlist names[2];
+
+  names[0].n_un.n_name = "_u";
+  names[1].n_un.n_name = NULL;
+  if (nlist ("/vmunix", names) == 0)
+    kernel_u_addr = names[0].n_value;
+  else
+    fatal ("Unable to get kernel u area address.");
+}
+#endif /* KERNEL_U_ADDR_BSD.  */
+
+#if defined (KERNEL_U_ADDR_HPUX)
+/* Get kernel_u_addr using HPUX-style nlist().  */
+CORE_ADDR kernel_u_addr;
+
+struct hpnlist {      
+        char *          n_name;
+        long            n_value;  
+        unsigned char   n_type;   
+        unsigned char   n_length;  
+        short           n_almod;   
+        short           n_unused;
+};
+static struct hpnlist nl[] = {{ "_u", -1, }, { (char *) 0, }};
+
+/* read the value of the u area from the hp-ux kernel */
+void _initialize_kernel_u_addr ()
+{
+    struct user u;
+    nlist ("/hp-ux", &nl);
+    kernel_u_addr = nl[0].n_value;
+}
+#endif /* KERNEL_U_ADDR_HPUX.  */
+
+#if !defined (offsetof)
+#define offsetof(TYPE, MEMBER) ((unsigned long) &((TYPE *)0)->MEMBER)
+#endif
+
+/* U_REGS_OFFSET is the offset of the registers within the u area.  */
+#if !defined (U_REGS_OFFSET)
+#define U_REGS_OFFSET \
+  ptrace (PT_READ_U, inferior_pid, \
+          (PTRACE_ARG3_TYPE) (offsetof (struct user, u_ar0)), 0, 0) \
+    - KERNEL_U_ADDR
+#endif
+
+/* Registers we shouldn't try to fetch.  */
+#if !defined (CANNOT_FETCH_REGISTER)
+#define CANNOT_FETCH_REGISTER(regno) 0
+#endif
+
+/* Fetch one register.  */
+
+static void
+fetch_register (regno)
+     int regno;
+{
+  register unsigned int regaddr;
+  char buf[MAX_REGISTER_RAW_SIZE];
+  char mess[128];                              /* For messages */
+  register int i;
+
+  /* Offset of registers within the u area.  */
+  unsigned int offset;
+
+  if (CANNOT_FETCH_REGISTER (regno))
+    {
+      bzero (buf, REGISTER_RAW_SIZE (regno));  /* Supply zeroes */
+      supply_register (regno, buf);
+      return;
+    }
+
+  offset = U_REGS_OFFSET;
+
+  regaddr = register_addr (regno, offset);
+  for (i = 0; i < REGISTER_RAW_SIZE (regno); i += sizeof (int))
+    {
+      errno = 0;
+      *(int *) &buf[i] = ptrace (PT_RUREGS, inferior_pid,
+                                (PTRACE_ARG3_TYPE) regaddr, 0, 0);
+      regaddr += sizeof (int);
+      if (errno != 0)
+       {
+         sprintf (mess, "reading register %s (#%d)", reg_names[regno], regno);
+         perror_with_name (mess);
+       }
+    }
+  supply_register (regno, buf);
+}
+
+
+
+/* Resume execution of the inferior process.
+   If STEP is nonzero, single-step it.
+   If SIGNAL is nonzero, give it that signal.  */
+
+void
+child_resume (step, signal)
+     int step;
+     int signal;
+{
+  errno = 0;
+
+  /* An address of (PTRACE_ARG3_TYPE) 1 tells ptrace to continue from where
+     it was. (If GDB wanted it to start some other way, we have already
+     written a new PC value to the child.)  */
+
+  if (step)
+    ptrace (PT_SINGLE, inferior_pid, (PTRACE_ARG3_TYPE) 1, signal, 0);
+  else
+    ptrace (PT_CONTIN, inferior_pid, (PTRACE_ARG3_TYPE) 1, signal, 0);
+
+  if (errno)
+    perror_with_name ("ptrace");
+}
+
+/* NOTE! I tried using PTRACE_READDATA, etc., to read and write memory
+   in the NEW_SUN_PTRACE case.
+   It ought to be straightforward.  But it appears that writing did
+   not write the data that I specified.  I cannot understand where
+   it got the data that it actually did write.  */
+
+/* Copy LEN bytes to or from inferior's memory starting at MEMADDR
+   to debugger memory starting at MYADDR.   Copy to inferior if
+   WRITE is nonzero.
+  
+   Returns the length copied, which is either the LEN argument or zero.
+   This xfer function does not do partial moves, since child_ops
+   doesn't allow memory operations to cross below us in the target stack
+   anyway.  */
+
+int
+child_xfer_memory (memaddr, myaddr, len, write, target)
+     CORE_ADDR memaddr;
+     char *myaddr;
+     int len;
+     int write;
+     struct target_ops *target;                /* ignored */
+{
+  register int i;
+  /* Round starting address down to longword boundary.  */
+  register CORE_ADDR addr = memaddr & - sizeof (int);
+  /* Round ending address up; get number of longwords that makes.  */
+  register int count
+    = (((memaddr + len) - addr) + sizeof (int) - 1) / sizeof (int);
+  /* Allocate buffer of that many longwords.  */
+  register int *buffer = (int *) alloca (count * sizeof (int));
+
+  if (write)
+    {
+      /* Fill start and end extra bytes of buffer with existing memory data.  */
+
+      if (addr != memaddr || len < (int)sizeof (int)) {
+       /* Need part of initial word -- fetch it.  */
+        buffer[0] = ptrace (PT_RIUSER, inferior_pid,
+                           (PTRACE_ARG3_TYPE) addr, 0, 0);
+      }
+
+      if (count > 1)           /* FIXME, avoid if even boundary */
+       {
+         buffer[count - 1]
+           = ptrace (PT_RIUSER, inferior_pid,
+                     (PTRACE_ARG3_TYPE) (addr + (count - 1) * sizeof (int)),
+                     0, 0);
+       }
+
+      /* Copy data to be written over corresponding part of buffer */
+
+      bcopy (myaddr, (char *) buffer + (memaddr & (sizeof (int) - 1)), len);
+
+      /* Write the entire buffer.  */
+
+      for (i = 0; i < count; i++, addr += sizeof (int))
+       {
+#if 0
+/* The HP-UX kernel crashes if you use PT_WDUSER to write into the text
+   segment.  FIXME -- does it work to write into the data segment using
+   WIUSER, or do these idiots really expect us to figure out which segment
+   the address is in, so we can use a separate system call for it??!  */
+         errno = 0;
+         ptrace (PT_WDUSER, inferior_pid, (PTRACE_ARG3_TYPE) addr,
+                 buffer[i], 0);
+         if (errno)
+#endif
+           {
+             /* Using the appropriate one (I or D) is necessary for
+                Gould NP1, at least.  */
+             errno = 0;
+             ptrace (PT_WIUSER, inferior_pid, (PTRACE_ARG3_TYPE) addr,
+                     buffer[i], 0);
+           }
+         if (errno)
+           return 0;
+       }
+    }
+  else
+    {
+      /* Read all the longwords */
+      for (i = 0; i < count; i++, addr += sizeof (int))
+       {
+         errno = 0;
+         buffer[i] = ptrace (PT_RIUSER, inferior_pid,
+                             (PTRACE_ARG3_TYPE) addr, 0, 0);
+         if (errno)
+           return 0;
+         QUIT;
+       }
+
+      /* Copy appropriate bytes out of the buffer.  */
+      bcopy ((char *) buffer + (memaddr & (sizeof (int) - 1)), myaddr, len);
+    }
+  return len;
+}
+
index 27bf9e9726fa283e5cb734b16300339486b09b1e..8b7dc61db90c33bf517c6388162ec9b01fc3070e 100644 (file)
@@ -50,7 +50,6 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.  */
 /*#include <sys/user.h>                After a.out.h  */
 #include <sys/file.h>
 #include <sys/stat.h>
-#include <sys/ptrace.h>
 #include <machine/psl.h>
 
 #ifdef KERNELDEBUG
diff --git a/gdb/nm-hppab.h b/gdb/nm-hppab.h
new file mode 100644 (file)
index 0000000..9dccb8f
--- /dev/null
@@ -0,0 +1,25 @@
+/* HPPA PA-RISC machine native support for BSD, for GDB.
+   Copyright 1991, 1992 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.  */
+
+#define U_REGS_OFFSET 0
+
+/* What a coincidence! */
+#define REGISTER_U_ADDR(addr, blockend, regno)                         \
+{ addr = (int)(blockend) + REGISTER_BYTE (regno);}
+
diff --git a/gdb/nm-hppah.h b/gdb/nm-hppah.h
new file mode 100644 (file)
index 0000000..6977a12
--- /dev/null
@@ -0,0 +1,24 @@
+/* Native support for HPPA-RISC machine running HPUX, for GDB.
+   Copyright 1991, 1992 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.  */
+
+#define U_REGS_OFFSET 0
+
+/* What a coincidence! */
+#define REGISTER_U_ADDR(addr, blockend, regno)                         \
+{ addr = (int)(blockend) + REGISTER_BYTE (regno);}
index f32687666c8e7eeff93c0069afab4eb4aac4ebcb..22f67d7ecaeccc71d418c9bff2dbf3ab15953c84 100644 (file)
@@ -35,12 +35,6 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.  */
 
 #define KERNEL_U_ADDR 0
 
-/* What a coincidence! */
-#define REGISTER_U_ADDR(addr, blockend, regno)                         \
-{ addr = (int)(blockend) + REGISTER_BYTE (regno);}
-
-#define U_REGS_OFFSET 0
-
 #ifndef SEEK_SET
 #  define SEEK_SET    0                /* Set file pointer to "offset" */
 #  define SEEK_CUR    1                /* Set file pointer to current plus "offset" */
index 462d0888fb8d2275b45c8cdd7c57f045485060c0..0c10fb650ebc9da49eafd46b9a043b2e01d0b337 100644 (file)
@@ -41,12 +41,6 @@ Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.  */
 
 #define KERNEL_U_ADDR 0
 
-/* What a coincidence! */
-#define REGISTER_U_ADDR(addr, blockend, regno)                         \
-{ addr = (int)(blockend) + REGISTER_BYTE (regno);}
-
-#define U_REGS_OFFSET 0
-
 /* HP uses non-ANSI definitions, but with void * results.  */
 #define        MEM_FNS_DECLARED        /* Some non-ANSI use void *, not char *.  */
 extern void *