* Makefile.in (ALLDEPFILES): Add sparc64nbsd-nat.c,
authorJason Thorpe <thorpej@netbsd.org>
Fri, 31 May 2002 00:59:15 +0000 (00:59 +0000)
committerJason Thorpe <thorpej@netbsd.org>
Fri, 31 May 2002 00:59:15 +0000 (00:59 +0000)
sparcnbsd-nat.c, and sparcnbsd-tdep.c.
(sparc64nbsd-nat.o)
(sparcnbsd-nat.o)
(sparcnbsd-tdep.o): New dependency lists.
* NEWS: Note new UltraSPARC NetBSD native configuration.
* configure.host (sparc64-*-netbsd*): New host.
* configure.tgt (sparc-*-netbsdelf*)
(sparc-*-netbsd*): Set gdb_target to nbsd.
(sparc64-*-netbsd*): New target.
* sparc64nbsd-nat.c: New file.
* sparcnbsd-nat.c: New file.
* sparcnbsd-tdep.c: New file.
* sparcnbsd-tdep.h: New file.
* config/sparc/nbsd.mt: New file.
* config/sparc/nbsd64.mh: New file.
* config/sparc/nbsd64.mt: New file.
* config/sparc/nbsdaout.mh (NATDEPFILES): Remove corelow.o,
sparc-nat.o, and solib.o.  Add sparcnbsd-nat.o.
(HOST_IPC): Remove.
* config/sparc/nbsdaout.mt: Remove.
* config/sparc/nbsdelf.mh (NATDEPFILES): Remove corelow.o,
sparc-nat.o, and solib.o.  Add sparcnbsd-nat.o.
(HOST_IPC): Remove.
* config/sparc/nbsdelf.mt: Remove.
* config/sparc/nm-nbsd.h: Update copyright years.  Remove all
sparc-nat.c compatiblity defines.
* config/sparc/tm-nbsd.h: Update copyright years.  Include solib.h.
(GDB_MULTI_ARCH): Set to GDB_MULTI_ARCH_PARTIAL.
* config/sparc/tm-nbsd64.h: New file.
* config/sparc/tm-nbsdaout.h: Remove.
* config/sparc/xm-nbsd.h: Remove.

21 files changed:
gdb/ChangeLog
gdb/Makefile.in
gdb/NEWS
gdb/config/sparc/nbsd.mt [new file with mode: 0644]
gdb/config/sparc/nbsd64.mh [new file with mode: 0644]
gdb/config/sparc/nbsd64.mt [new file with mode: 0644]
gdb/config/sparc/nbsdaout.mh
gdb/config/sparc/nbsdaout.mt [deleted file]
gdb/config/sparc/nbsdelf.mh
gdb/config/sparc/nbsdelf.mt [deleted file]
gdb/config/sparc/nm-nbsd.h
gdb/config/sparc/tm-nbsd.h
gdb/config/sparc/tm-nbsd64.h [new file with mode: 0644]
gdb/config/sparc/tm-nbsdaout.h [deleted file]
gdb/config/sparc/xm-nbsd.h [deleted file]
gdb/configure.host
gdb/configure.tgt
gdb/sparc64nbsd-nat.c [new file with mode: 0644]
gdb/sparcnbsd-nat.c [new file with mode: 0644]
gdb/sparcnbsd-tdep.c [new file with mode: 0644]
gdb/sparcnbsd-tdep.h [new file with mode: 0644]

index 7af9b8045476bc83694dceefe37620e5368d6c5e..0be6082f5e7a88fefc19f54c8a1c3f6aa3904acd 100644 (file)
@@ -1,3 +1,38 @@
+2002-05-30  Jason Thorpe  <thorpej@wasabisystems.com>
+
+       * Makefile.in (ALLDEPFILES): Add sparc64nbsd-nat.c,
+       sparcnbsd-nat.c, and sparcnbsd-tdep.c.
+       (sparc64nbsd-nat.o)
+       (sparcnbsd-nat.o)
+       (sparcnbsd-tdep.o): New dependency lists.
+       * NEWS: Note new UltraSPARC NetBSD native configuration.
+       * configure.host (sparc64-*-netbsd*): New host.
+       * configure.tgt (sparc-*-netbsdelf*)
+       (sparc-*-netbsd*): Set gdb_target to nbsd.
+       (sparc64-*-netbsd*): New target.
+       * sparc64nbsd-nat.c: New file.
+       * sparcnbsd-nat.c: New file.
+       * sparcnbsd-tdep.c: New file.
+       * sparcnbsd-tdep.h: New file.
+       * config/sparc/nbsd.mt: New file.
+       * config/sparc/nbsd64.mh: New file.
+       * config/sparc/nbsd64.mt: New file.
+       * config/sparc/nbsdaout.mh (NATDEPFILES): Remove corelow.o,
+       sparc-nat.o, and solib.o.  Add sparcnbsd-nat.o.
+       (HOST_IPC): Remove.
+       * config/sparc/nbsdaout.mt: Remove.
+       * config/sparc/nbsdelf.mh (NATDEPFILES): Remove corelow.o,
+       sparc-nat.o, and solib.o.  Add sparcnbsd-nat.o.
+       (HOST_IPC): Remove.
+       * config/sparc/nbsdelf.mt: Remove.
+       * config/sparc/nm-nbsd.h: Update copyright years.  Remove all
+       sparc-nat.c compatiblity defines.
+       * config/sparc/tm-nbsd.h: Update copyright years.  Include solib.h.
+       (GDB_MULTI_ARCH): Set to GDB_MULTI_ARCH_PARTIAL.
+       * config/sparc/tm-nbsd64.h: New file.
+       * config/sparc/tm-nbsdaout.h: Remove.
+       * config/sparc/xm-nbsd.h: Remove.
+
 2002-05-30  Jason Thorpe  <thorpej@wasabisystems.com>
 
        * Makefile.in (sparc-tdep.o): Add osabi.h to dependency list.
index 8658b6aa5e967b386b94242c620dd87d38cda118..1919422844538b89efd5676d215f215528387030 100644 (file)
@@ -1241,6 +1241,7 @@ ALLDEPFILES = 29k-share/udi/udip2soc.c 29k-share/udi/udr.c \
        sh-tdep.c shnbsd-tdep.c shnbsd-nat.c \
        solib.c solib-svr4.c solib-sunos.c sparc-linux-nat.c \
        sparc-nat.c \
+       sparc64nbsd-nat.c sparcnbsd-nat.c sparcnbsd-tdep.c \
        sparc-tdep.c sparcl-tdep.c sun3-nat.c \
        symm-tdep.c symm-nat.c \
        vax-tdep.c \
@@ -2128,6 +2129,16 @@ sparc-tdep.o: sparc-tdep.c $(floatformat_h) $(defs_h) $(gdbcore_h) \
 
 sparcl-tdep.o: sparcl-tdep.c $(defs_h) $(gdbcore_h) $(target_h) $(regcache_h)
 
+sparc64nbsd-nat.o: sparc64nbsd-nat.c $(defs_h) $(inferior_h) $(regcache_h) \
+       sparcnbsd-tdep.h
+
+sparcnbsd-nat.o: sparcnbsd-nat.c $(defs_h) $(inferior_h) $(regcache_h) \
+       sparcnbsd-tdep.h 
+
+sparcnbsd-tdep.o: sparcnbsd-tdep.c $(defs_h) $(gdbcore_h) $(regcache_h) \
+       $(target_h) $(value_h) osabi.h sparcnbsd-tdep.h nbsd-tdep.h \
+       solib-svr4.h
+
 xstormy16-tdep.o: xstormy16-tdep.c $(defs_h) $(value_h) $(inferior_h) \
        $(symfile_h) $(arch_utils_h) $(regcache_h) $(gdbcore_h)
 
index a61b435c6877d76c960fcc66d1ceae6c411162b5..4ad34d4d91240206989463be6f78264f8decf038 100644 (file)
--- a/gdb/NEWS
+++ b/gdb/NEWS
@@ -41,6 +41,7 @@ Atmel AVR                                     avr*-*-*
 Alpha NetBSD                                   alpha*-*-netbsd*
 SH NetBSD                                      sh*-*-netbsdelf*
 MIPS NetBSD                                    mips*-*-netbsd*
+UltraSPARC NetBSD                              sparc64-*-netbsd*
 
 * OBSOLETE configurations and files
 
diff --git a/gdb/config/sparc/nbsd.mt b/gdb/config/sparc/nbsd.mt
new file mode 100644 (file)
index 0000000..b04dd42
--- /dev/null
@@ -0,0 +1,4 @@
+# Target: SPARC running NetBSD
+TDEPFILES= sparc-tdep.o sparcnbsd-tdep.o nbsd-tdep.o corelow.o solib.o \
+       solib-svr4.o
+TM_FILE= tm-nbsd.h
diff --git a/gdb/config/sparc/nbsd64.mh b/gdb/config/sparc/nbsd64.mh
new file mode 100644 (file)
index 0000000..eb54e48
--- /dev/null
@@ -0,0 +1,3 @@
+# Host: UltraSPARC running NetBSD
+NATDEPFILES= fork-child.o infptrace.o inftarg.o sparc64nbsd-nat.o
+NAT_FILE= nm-nbsd.h
diff --git a/gdb/config/sparc/nbsd64.mt b/gdb/config/sparc/nbsd64.mt
new file mode 100644 (file)
index 0000000..93b8f78
--- /dev/null
@@ -0,0 +1,4 @@
+# Target: UltraSPARC running NetBSD
+TDEPFILES= sparc-tdep.o sparcnbsd-tdep.o nbsd-tdep.o corelow.o solib.o \
+       solib-svr4.o
+TM_FILE= tm-nbsd64.h
index ecb69e473da011107247c3f39144f1c0ef37c511..4520899812475f740af0e0a665adf2d79ad23c6f 100644 (file)
@@ -1,6 +1,4 @@
 # Host: Sun 4 or Sparcstation, running NetBSD
-NATDEPFILES= fork-child.o infptrace.o inftarg.o corelow.o sparc-nat.o \
-       solib.o solib-sunos.o
+NATDEPFILES= fork-child.o infptrace.o inftarg.o sparcnbsd-nat.o solib-sunos.o
 XM_FILE= xm-nbsd.h
 NAT_FILE= nm-nbsdaout.h
-HOST_IPC=-DBSD_IPC
diff --git a/gdb/config/sparc/nbsdaout.mt b/gdb/config/sparc/nbsdaout.mt
deleted file mode 100644 (file)
index c603f36..0000000
+++ /dev/null
@@ -1,3 +0,0 @@
-# Target: Sun 4 or Sparcstation, running NetBSD
-TDEPFILES= sparc-tdep.o
-TM_FILE= tm-nbsdaout.h
index 8581c1b92ab6c00555d308502cc738c3b01d90c7..1042d91b9ddfbc01086babc2ed05e3a1b415ed9f 100644 (file)
@@ -1,6 +1,4 @@
 # Host: Sun 4 or Sparcstation, running NetBSD
-NATDEPFILES= fork-child.o infptrace.o inftarg.o corelow.o sparc-nat.o \
-       solib.o solib-svr4.o solib-legacy.o
+NATDEPFILES= fork-child.o infptrace.o inftarg.o sparcnbsd-nat.o
 XM_FILE= xm-nbsd.h
 NAT_FILE= nm-nbsd.h
-HOST_IPC=-DBSD_IPC
diff --git a/gdb/config/sparc/nbsdelf.mt b/gdb/config/sparc/nbsdelf.mt
deleted file mode 100644 (file)
index 5c89318..0000000
+++ /dev/null
@@ -1,3 +0,0 @@
-# Target: Sun 4 or Sparcstation, running NetBSD
-TDEPFILES= sparc-tdep.o
-TM_FILE= tm-nbsd.h
index 653be852d85c1989dcc0f4f71d64d22d23fb1089..957a34ed141958a55fd112cfcdada67329a1268a 100644 (file)
@@ -1,5 +1,5 @@
 /* Native-dependent definitions for Sparc running NetBSD, for GDB.
-   Copyright 1986, 1987, 1989, 1992, 1994, 1996, 1999, 2000
+   Copyright 1986, 1987, 1989, 1992, 1994, 1996, 1999, 2000, 2002
    Free Software Foundation, Inc.
 
    This file is part of GDB.
 
 #define CHILD_PREPARE_TO_STORE() read_register_bytes (0, NULL, REGISTER_BYTES)
 
-/* Make things match up with what is expected in sparc-nat.c.  */
-
-#define regs           trapframe
-#define fp_status      fpstate
-
-#define r_g1           tf_global[1]
-#define r_ps           tf_psr
-#define r_pc           tf_pc
-#define r_npc          tf_npc
-#define r_y            tf_y
-
-#define fpu            fpstate
-#define fpu_regs       fs_regs
-#define fpu_fsr                fs_fsr
-#define fpu_fr         fs_regs
-#define Fpu_fsr                fs_fsr
-#define FPU_FSR_TYPE   int
-
-#define PTRACE_GETREGS  PT_GETREGS
-#define PTRACE_GETFPREGS PT_GETFPREGS
-#define PTRACE_SETREGS  PT_SETREGS
-#define PTRACE_SETFPREGS PT_SETFPREGS
-
-#define GDB_GREGSET_T  struct reg
-#define GDB_FPREGSET_T struct fpreg
-
 #endif /* NM_NBSD_H */
index 289e705f0a9028c35ac3a0f65c732fe4fa3fe138..bd9845029b5b4e4dcde53ad73ff8fa3269d05181 100644 (file)
@@ -1,5 +1,5 @@
 /* Macro definitions for Sparc running under NetBSD.
-   Copyright 1994 Free Software Foundation, Inc.
+   Copyright 1994, 2002 Free Software Foundation, Inc.
 
    This file is part of GDB.
 
@@ -21,6 +21,9 @@
 #ifndef TM_NBSD_H
 #define TM_NBSD_H
 
+#define GDB_MULTI_ARCH GDB_MULTI_ARCH_PARTIAL
+
 #include "sparc/tm-sparc.h"
+#include "solib.h"
 
 #endif /* TM_NBSD_H */
diff --git a/gdb/config/sparc/tm-nbsd64.h b/gdb/config/sparc/tm-nbsd64.h
new file mode 100644 (file)
index 0000000..cc1d6b3
--- /dev/null
@@ -0,0 +1,27 @@
+/* Macro definitions for UltraSPARC running under NetBSD.
+   Copyright 1994, 2002 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., 59 Temple Place - Suite 330,
+   Boston, MA 02111-1307, USA.  */
+
+#ifndef TM_NBSD64_H
+#define TM_NBSD64_H
+
+#include "sparc/tm-sp64.h" /* sets GDB_MULTI_ARCH */
+#include "solib.h"
+
+#endif /* TM_NBSD64_H */
diff --git a/gdb/config/sparc/tm-nbsdaout.h b/gdb/config/sparc/tm-nbsdaout.h
deleted file mode 100644 (file)
index a62e535..0000000
+++ /dev/null
@@ -1,30 +0,0 @@
-/* Macro definitions for Sparc running under NetBSD.
-   Copyright 1994, 2002 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., 59 Temple Place - Suite 330,
-   Boston, MA 02111-1307, USA.  */
-
-#ifndef TM_NBSDAOUT_H
-#define TM_NBSDAOUT_H
-
-#include "sparc/tm-nbsd.h"
-
-/* Return non-zero if we are in a shared library trampoline code stub. */
-#define IN_SOLIB_CALL_TRAMPOLINE(pc, name) \
-  (name && !strcmp(name, "_DYNAMIC"))
-
-#endif /* TM_NBSDAOUT_H */
diff --git a/gdb/config/sparc/xm-nbsd.h b/gdb/config/sparc/xm-nbsd.h
deleted file mode 100644 (file)
index e469aab..0000000
+++ /dev/null
@@ -1,22 +0,0 @@
-/* Parameters for execution on a Sparc running NetBSD, for GDB.
-   Copyright 1994 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., 59 Temple Place - Suite 330,
-   Boston, MA 02111-1307, USA.  */
-
-/* Get generic NetBSD host definitions. */
-#include "xm-nbsd.h"
index 16f6a52c164bbc30227e1a5419d279bcb88c9cd8..4256db32134a0a7df2ba97b13e86e071c1dfd403 100644 (file)
@@ -153,6 +153,7 @@ sparc-*-*)          gdb_host=sun4os4 ;;
 sparc64-*-freebsd*|ultrasparc-*-freebsd*|sparcv9-*-freebsd*)
                        gdb_host=fbsd ;;
 sparc64-*-linux*)      gdb_host=linux ;;
+sparc64-*-netbsd*)     gdb_host=nbsd64 ;;
 sparcv9-*-* | sparc64-*-*) gdb_host=sun4sol2 ;;
 
 strongarm-*-*)         gdb_host=arm ;;
index 8861967e16b3704bec3fb194ad14653430507185..129fa49ee8c9ec822562d5dcee3de2e54cb7abfb 100644 (file)
@@ -259,8 +259,7 @@ sparc-*-coff*)              gdb_target=sparc-em ;;
 sparc-*-elf*)          gdb_target=sparc-em ;;
 sparc-*-linux*)                gdb_target=linux ;;
 sparc-*-lynxos*)       gdb_target=sparclynx ;;
-sparc-*-netbsdelf*)    gdb_target=nbsdelf ;;
-sparc-*-netbsd*)       gdb_target=nbsdaout ;;
+sparc-*-netbsd*)       gdb_target=nbsd ;;
 sparc-*-solaris2*)     gdb_target=sun4sol2 ;;
 sparc-*-sunos4*)       gdb_target=sun4os4 ;;
 sparc-*-sunos5*)       gdb_target=sun4sol2 ;;
@@ -278,6 +277,7 @@ sparc86x-*-*)               gdb_target=sparclite ;;
 sparc64-*-freebsd*|ultrasparc-*-freebsd*|sparcv9-*-freebsd*)
                        gdb_target=fbsd ;;
 sparc64-*-linux*)      gdb_target=sp64linux ;;
+sparc64-*-netbsd*)     gdb_target=nbsd64 ;;
 sparcv9-*-* | sparc64-*-*) gdb_target=sp64 ;;
 
 xstormy16-*-*)          gdb_target=xstormy16 ;;
diff --git a/gdb/sparc64nbsd-nat.c b/gdb/sparc64nbsd-nat.c
new file mode 100644 (file)
index 0000000..a991d0e
--- /dev/null
@@ -0,0 +1,207 @@
+/* Native-dependent code for UltraSPARC systems running NetBSD.
+   Copyright 2002 Free Software Foundation, Inc.
+   Contributed by Wasabi Systems, 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., 59 Temple Place - Suite 330,
+   Boston, MA 02111-1307, USA.  */
+
+#include "defs.h"
+#include "inferior.h"
+#include "regcache.h"
+
+#include "sparcnbsd-tdep.h"
+
+#include <sys/types.h>
+#include <sys/ptrace.h>
+#include <machine/reg.h>
+
+/* NOTE: We don't bother with any of the deferred_store nonsense; it
+   makes things a lot more complicated than they need to be.  */
+
+/* Determine if PT_GETREGS fetches this register.  */
+static int
+getregs_supplies (int regno)
+{
+  /* FIXME: PS_REGNUM for 32-bit code.  */
+  return (regno == TSTATE_REGNUM
+         || regno == PC_REGNUM
+         || regno == NPC_REGNUM
+         || regno == Y_REGNUM
+         || (regno >= G0_REGNUM && regno <= G7_REGNUM)
+         || (regno >= O0_REGNUM && regno <= O7_REGNUM)
+         /* stack regs (handled by sparcnbsd_supply_reg)  */
+         || (regno >= L0_REGNUM && regno <= I7_REGNUM));
+}
+
+/* Determine if PT_GETFPREGS fetches this register.  */
+static int
+getfpregs_supplies (int regno)
+{
+  return ((regno >= FP0_REGNUM && regno <= (FP0_REGNUM + 47))
+         || regno == FPS_REGNUM);
+}
+
+void
+fetch_inferior_registers (int regno)
+{
+  /* We don't use deferred stores.  */
+  if (deferred_stores)
+    internal_error (__FILE__, __LINE__,
+                   "fetch_inferior_registers: deferred stores pending");
+
+  if (regno == -1 || getregs_supplies (regno))
+    {
+      union {
+       struct reg32 regs32;
+       struct reg64 regs64;
+      } regs;
+
+      if (ptrace (PT_GETREGS, PIDGET (inferior_ptid),
+                 (PTRACE_ARG3_TYPE) &regs, 0) == -1)
+        perror_with_name ("Couldn't get registers");
+
+      if (gdbarch_ptr_bit (current_gdbarch) == 32)
+        sparcnbsd_supply_reg32 ((char *) &regs.regs32, regno);
+      else
+       sparcnbsd_supply_reg64 ((char *) &regs.regs64, regno);
+      if (regno != -1)
+       return;
+    }
+
+  if (regno == -1 || getfpregs_supplies (regno))
+    {
+      union {
+        struct fpreg32 fpregs32;
+       struct fpreg64 fpregs64;
+      } fpregs;
+
+      if (ptrace (PT_GETFPREGS, PIDGET (inferior_ptid),
+                 (PTRACE_ARG3_TYPE) &fpregs, 0) == -1)
+        perror_with_name ("Couldn't get floating point registers");
+
+      if (gdbarch_ptr_bit (current_gdbarch) == 32)
+        sparcnbsd_supply_fpreg32 ((char *) &fpregs.fpregs32, regno);
+      else
+        sparcnbsd_supply_fpreg64 ((char *) &fpregs.fpregs64, regno);
+      if (regno != -1)
+       return;
+    }
+}
+
+void
+store_inferior_registers (int regno)
+{
+  /* We don't use deferred stores.  */
+  if (deferred_stores)
+    internal_error (__FILE__, __LINE__,
+                   "store_inferior_registers: deferred stores pending");
+
+  if (regno == -1 || getregs_supplies (regno))
+    {
+      union {
+       struct reg32 regs32;
+       struct reg64 regs64;
+      } regs;
+
+      if (ptrace (PT_GETREGS, PIDGET (inferior_ptid),
+                 (PTRACE_ARG3_TYPE) &regs, 0) == -1)
+       perror_with_name ("Couldn't get registers");
+
+      if (gdbarch_ptr_bit (current_gdbarch) == 32)
+        sparcnbsd_fill_reg32 ((char *) &regs.regs32, regno);
+      else
+       sparcnbsd_fill_reg64 ((char *) &regs.regs64, regno);
+
+      if (ptrace (PT_SETREGS, PIDGET (inferior_ptid),
+                 (PTRACE_ARG3_TYPE) &regs, 0) == -1)
+       perror_with_name ("Couldn't write registers");
+
+      /* Deal with the stack regs.  */
+      if (regno == -1 || regno == SP_REGNUM
+         || (regno >= L0_REGNUM && regno <= I7_REGNUM))
+       {
+         CORE_ADDR sp = read_register (SP_REGNUM);
+         int i;
+         char buf[8];
+
+         if (sp & 1)
+           {
+             /* Registers are 64-bit.  */
+             sp += 2047;
+
+             for (i = L0_REGNUM; i <= I7_REGNUM; i++)
+               {
+                 if (regno == -1 || regno == SP_REGNUM || regno == i)
+                   {
+                     regcache_collect (i, buf);
+                     target_write_memory (sp + ((i - L0_REGNUM) * 8),
+                                          buf, sizeof (buf));
+                   }
+               }
+            }
+         else
+           {
+             /* Registers are 32-bit.  Toss any sign-extension of the stack
+                pointer.
+
+                FIXME: We don't currently handle 32-bit code in a binary
+                that indicated LP64.  Do we have to care about that?  */
+              if (gdbarch_ptr_bit (current_gdbarch) != 32)
+               internal_error
+                   (__FILE__, __LINE__,
+                   "store_inferior_registers: 32-bit code in 64-bit inferior");
+
+             sp &= 0xffffffffUL;
+             for (i = L0_REGNUM; i <= I7_REGNUM; i++)
+               {
+                 if (regno == -1 || regno == SP_REGNUM || regno == i)
+                   {
+                     regcache_collect (i, buf);
+                     target_write_memory (sp + ((i - L0_REGNUM) * 4), buf, 4);
+                   }
+               }
+           }
+       }
+
+      if (regno != -1)
+       return;
+    }
+
+  if (regno == -1 || getfpregs_supplies (regno))
+    {
+      union {
+       struct fpreg32 fpregs32;
+       struct fpreg64 fpregs64;
+      } fpregs;
+
+      if (ptrace (PT_GETFPREGS, PIDGET (inferior_ptid),
+                 (PTRACE_ARG3_TYPE) &fpregs, 0) == -1)
+       perror_with_name ("Couldn't get floating point registers");
+
+      if (gdbarch_ptr_bit (current_gdbarch) == 32)
+        sparcnbsd_fill_fpreg32 ((char *) &fpregs.fpregs32, regno);
+      else
+       sparcnbsd_fill_fpreg64 ((char *) &fpregs.fpregs64, regno);
+      
+      if (ptrace (PT_SETFPREGS, PIDGET (inferior_ptid),
+                 (PTRACE_ARG3_TYPE) &fpregs, 0) == -1)
+       perror_with_name ("Couldn't write floating point registers");
+
+      if (regno != -1)
+       return;
+    }
+}
diff --git a/gdb/sparcnbsd-nat.c b/gdb/sparcnbsd-nat.c
new file mode 100644 (file)
index 0000000..ce5d44d
--- /dev/null
@@ -0,0 +1,154 @@
+/* Native-dependent code for SPARC systems running NetBSD.
+   Copyright 2002 Free Software Foundation, Inc.
+   Contributed by Wasabi Systems, 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., 59 Temple Place - Suite 330,
+   Boston, MA 02111-1307, USA.  */
+
+#include "defs.h"
+#include "inferior.h"
+#include "regcache.h"
+
+#include "sparcnbsd-tdep.h"
+
+#include <sys/types.h>
+#include <sys/ptrace.h>
+#include <machine/reg.h>
+
+/* NOTE: We don't bother with any of the deferred_store nonsense; it
+   makes things a lot more complicated than they need to be.  */
+
+/* Determine if PT_GETREGS fetches this register.  */
+static int
+getregs_supplies (int regno)
+{
+  return (regno == PS_REGNUM
+         || regno == PC_REGNUM
+         || regno == NPC_REGNUM
+         || regno == Y_REGNUM
+         || (regno >= G0_REGNUM && regno <= G7_REGNUM)
+         || (regno >= O0_REGNUM && regno <= O7_REGNUM)
+         /* stack regs (handled by sparcnbsd_supply_reg)  */
+         || (regno >= L0_REGNUM && regno <= I7_REGNUM));
+}
+
+/* Determine if PT_GETFPREGS fetches this register.  */
+static int
+getfpregs_supplies (int regno)
+{
+  return ((regno >= FP0_REGNUM && regno <= (FP0_REGNUM + 31))
+         || regno == FPS_REGNUM);
+}
+
+void
+fetch_inferior_registers (int regno)
+{
+  /* We don't use deferred stores.  */
+  if (deferred_stores)
+    internal_error (__FILE__, __LINE__,
+                   "fetch_inferior_registers: deferred stores pending");
+
+  if (regno == -1 || getregs_supplies (regno))
+    {
+      struct reg regs;
+
+      if (ptrace (PT_GETREGS, PIDGET (inferior_ptid),
+                 (PTRACE_ARG3_TYPE) &regs, 0) == -1)
+        perror_with_name ("Couldn't get registers");
+
+      sparcnbsd_supply_reg32 ((char *) &regs, regno);
+      if (regno != -1)
+       return;
+    }
+
+  if (regno == -1 || getfpregs_supplies (regno))
+    {
+      struct fpreg fpregs;
+
+      if (ptrace (PT_GETFPREGS, PIDGET (inferior_ptid),
+                 (PTRACE_ARG3_TYPE) &fpregs, 0) == -1)
+        perror_with_name ("Couldn't get floating point registers");
+
+      sparcnbsd_supply_fpreg32 ((char *) &fpregs, regno);
+      if (regno != -1)
+       return;
+    }
+}
+
+void
+store_inferior_registers (int regno)
+{
+  /* We don't use deferred stores.  */
+  if (deferred_stores)
+    internal_error (__FILE__, __LINE__,
+                   "store_inferior_registers: deferred stores pending");
+
+  if (regno == -1 || getregs_supplies (regno))
+    {
+      struct reg regs;
+
+      if (ptrace (PT_GETREGS, PIDGET (inferior_ptid),
+                 (PTRACE_ARG3_TYPE) &regs, 0) == -1)
+       perror_with_name ("Couldn't get registers");
+
+      sparcnbsd_fill_reg32 ((char *) &regs, regno);
+
+      if (ptrace (PT_SETREGS, PIDGET (inferior_ptid),
+                 (PTRACE_ARG3_TYPE) &regs, 0) == -1)
+       perror_with_name ("Couldn't write registers");
+
+      /* Deal with the stack regs.  */
+      if (regno == -1 || regno == SP_REGNUM
+         || (regno >= L0_REGNUM && regno <= I7_REGNUM))
+       {
+         CORE_ADDR sp = read_register (SP_REGNUM);
+         int i;
+         char buf[4];
+
+         for (i = L0_REGNUM; i <= I7_REGNUM; i++)
+           {
+             if (regno == -1 || regno == SP_REGNUM || regno == i)
+               {
+                 regcache_collect (i, buf);
+                 target_write_memory (sp + ((i - L0_REGNUM) * 4),
+                                      buf, sizeof (buf));
+               }
+           }
+       }
+
+      if (regno != -1)
+       return;
+    }
+
+  if (regno == -1 || getfpregs_supplies (regno))
+    {
+      struct fpreg fpregs;
+
+      if (ptrace (PT_GETFPREGS, PIDGET (inferior_ptid),
+                 (PTRACE_ARG3_TYPE) &fpregs, 0) == -1)
+       perror_with_name ("Couldn't get floating point registers");
+
+      sparcnbsd_fill_fpreg32 ((char *) &fpregs, regno);
+      
+      if (ptrace (PT_SETFPREGS, PIDGET (inferior_ptid),
+                 (PTRACE_ARG3_TYPE) &fpregs, 0) == -1)
+       perror_with_name ("Couldn't write floating point registers");
+
+      if (regno != -1)
+       return;
+    }
+}
diff --git a/gdb/sparcnbsd-tdep.c b/gdb/sparcnbsd-tdep.c
new file mode 100644 (file)
index 0000000..ea70e51
--- /dev/null
@@ -0,0 +1,531 @@
+/* Target-dependent code for SPARC systems running NetBSD.
+   Copyright 2002 Free Software Foundation, Inc.
+   Contributed by Wasabi Systems, 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., 59 Temple Place - Suite 330,
+   Boston, MA 02111-1307, USA.  */
+
+#include "defs.h"
+#include "gdbcore.h"
+#include "regcache.h"
+#include "target.h"
+#include "value.h"
+#include "osabi.h"
+
+#include "sparcnbsd-tdep.h"
+#include "nbsd-tdep.h"
+
+#include "solib-svr4.h"
+
+#define REG32_OFFSET_PSR       (0 * 4)
+#define REG32_OFFSET_PC                (1 * 4)
+#define REG32_OFFSET_NPC       (2 * 4)
+#define REG32_OFFSET_Y         (3 * 4)
+#define REG32_OFFSET_GLOBAL    (4 * 4)
+#define REG32_OFFSET_OUT       (12 * 4)
+
+#define REG64_OFFSET_TSTATE    (0 * 8)
+#define REG64_OFFSET_PC                (1 * 8)
+#define REG64_OFFSET_NPC       (2 * 8)
+#define REG64_OFFSET_Y         (3 * 8)
+#define REG64_OFFSET_GLOBAL    (4 * 8)
+#define REG64_OFFSET_OUT       (12 * 8)
+
+void
+sparcnbsd_supply_reg32 (char *regs, int regno)
+{
+  int i;
+
+  if (regno == PS_REGNUM || regno == -1)
+    supply_register (PS_REGNUM, regs + REG32_OFFSET_PSR);
+
+  if (regno == PC_REGNUM || regno == -1)
+    supply_register (PC_REGNUM, regs + REG32_OFFSET_PC);
+
+  if (regno == NPC_REGNUM || regno == -1)
+    supply_register (NPC_REGNUM, regs + REG32_OFFSET_NPC);
+
+  if (regno == Y_REGNUM || regno == -1)
+    supply_register (Y_REGNUM, regs + REG32_OFFSET_Y);
+
+  if ((regno >= G0_REGNUM && regno <= G7_REGNUM) || regno == -1)
+    {
+      if (regno == G0_REGNUM || regno == -1)
+       supply_register (G0_REGNUM, NULL);      /* %g0 is always zero */
+      for (i = G1_REGNUM; i <= G7_REGNUM; i++)
+       {
+         if (regno == i || regno == -1)
+           supply_register (i, regs + REG32_OFFSET_GLOBAL +
+                            ((i - G0_REGNUM) * 4));
+       }
+    }
+
+  if ((regno >= O0_REGNUM && regno <= O7_REGNUM) || regno == -1)
+    {
+      for (i = O0_REGNUM; i <= O7_REGNUM; i++)
+       {
+         if (regno == i || regno == -1)
+           supply_register (i, regs + REG32_OFFSET_OUT +
+                            ((i - O0_REGNUM) * 4));
+        }
+    }
+
+  /* Inputs and Locals are stored onto the stack by by the kernel.  */
+  if ((regno >= L0_REGNUM && regno <= I7_REGNUM) || regno == -1)
+    {
+      CORE_ADDR sp = read_register (SP_REGNUM);
+      char buf[4];
+
+      for (i = L0_REGNUM; i <= I7_REGNUM; i++)
+       {
+         if (regno == i || regno == -1)
+           {
+              target_read_memory (sp + ((i - L0_REGNUM) * 4),
+                                  buf, sizeof (buf));
+             supply_register (i, buf);
+           }
+       }
+    }
+
+  /* FIXME: If we don't set these valid, read_register_bytes() rereads
+     all the regs every time it is called!  */
+  if (regno == WIM_REGNUM || regno == -1)
+    supply_register (WIM_REGNUM, NULL);
+  if (regno == TBR_REGNUM || regno == -1)
+    supply_register (TBR_REGNUM, NULL);
+  if (regno == CPS_REGNUM || regno == -1)
+    supply_register (CPS_REGNUM, NULL);
+}
+
+void
+sparcnbsd_supply_reg64 (char *regs, int regno)
+{
+  int i;
+  char buf[8];
+
+  if (regno == TSTATE_REGNUM || regno == -1)
+    supply_register (PS_REGNUM, regs + REG64_OFFSET_TSTATE);
+
+  if (regno == PC_REGNUM || regno == -1)
+    supply_register (PC_REGNUM, regs + REG64_OFFSET_PC);
+
+  if (regno == NPC_REGNUM || regno == -1)
+    supply_register (NPC_REGNUM, regs + REG64_OFFSET_NPC);
+
+  if (regno == Y_REGNUM || regno == -1)
+    {
+      memset (buf, 0, sizeof (buf));
+      memcpy (&buf[4], regs + REG64_OFFSET_Y, 4);
+      supply_register (Y_REGNUM, buf);
+    }
+
+  if ((regno >= G0_REGNUM && regno <= G7_REGNUM) || regno == -1)
+    {
+      if (regno == G0_REGNUM || regno == -1)
+       supply_register (G0_REGNUM, NULL);      /* %g0 is always zero */
+      for (i = G1_REGNUM; i <= G7_REGNUM; i++)
+       {
+         if (regno == i || regno == -1)
+           supply_register (i, regs + REG64_OFFSET_GLOBAL +
+                            ((i - G0_REGNUM) * 8));
+       }
+    }
+
+  if ((regno >= O0_REGNUM && regno <= O7_REGNUM) || regno == -1)
+    {
+      for (i = O0_REGNUM; i <= O7_REGNUM; i++)
+       {
+         if (regno == i || regno == -1)
+           supply_register (i, regs + REG64_OFFSET_OUT +
+                            ((i - O0_REGNUM) * 8));
+        }
+    }
+
+  /* Inputs and Locals are stored onto the stack by by the kernel.  */
+  if ((regno >= L0_REGNUM && regno <= I7_REGNUM) || regno == -1)
+    {
+      CORE_ADDR sp = read_register (SP_REGNUM);
+      char buf[8];
+
+      if (sp & 1)
+       {
+         /* Registers are 64-bit.  */
+         sp += 2047;
+
+         for (i = L0_REGNUM; i <= I7_REGNUM; i++)
+           {
+             if (regno == i || regno == -1)
+               {
+                  target_read_memory (sp + ((i - L0_REGNUM) * 8),
+                                      buf, sizeof (buf));
+                 supply_register (i, buf);
+               }
+           }
+       }
+      else
+       {
+         /* Registers are 32-bit.  Toss any sign-extension of the stack
+            pointer, clear out the top half of the temporary buffer, and
+            put the register value in the bottom half.  */
+
+         sp &= 0xffffffffUL;
+         memset (buf, 0, sizeof (buf));
+         for (i = L0_REGNUM; i <= I7_REGNUM; i++)
+           {
+             if (regno == i || regno == -1)
+               {
+                 target_read_memory (sp + ((i - L0_REGNUM) * 4),
+                                     &buf[4], sizeof (buf));
+                  supply_register (i, buf);
+               }
+           }
+       }
+    }
+
+  /* FIXME: If we don't set these valid, read_register_bytes() rereads
+     all the regs every time it is called!  */
+  if (regno == WIM_REGNUM || regno == -1)
+    supply_register (WIM_REGNUM, NULL);
+  if (regno == TBR_REGNUM || regno == -1)
+    supply_register (TBR_REGNUM, NULL);
+  if (regno == CPS_REGNUM || regno == -1)
+    supply_register (CPS_REGNUM, NULL);
+}
+
+void
+sparcnbsd_fill_reg32 (char *regs, int regno)
+{
+  int i;
+
+  if (regno == PS_REGNUM || regno == -1)
+    regcache_collect (PS_REGNUM, regs + REG32_OFFSET_PSR);
+
+  if (regno == PC_REGNUM || regno == -1)
+    regcache_collect (PC_REGNUM, regs + REG32_OFFSET_PC);
+
+  if (regno == NPC_REGNUM || regno == -1)
+    regcache_collect (NPC_REGNUM, regs + REG32_OFFSET_NPC);
+
+  if (regno == Y_REGNUM || regno == -1)
+    regcache_collect (Y_REGNUM, regs + REG32_OFFSET_Y);
+
+  if ((regno >= G0_REGNUM && regno <= G7_REGNUM) || regno == -1)
+    {
+      /* %g0 is always zero */
+      for (i = G1_REGNUM; i <= G7_REGNUM; i++)
+       {
+         if (regno == i || regno == -1)
+           regcache_collect (i, regs + REG32_OFFSET_GLOBAL +
+                             ((i - G0_REGNUM) * 4));
+       }
+    }
+
+  if ((regno >= O0_REGNUM && regno <= O7_REGNUM) || regno == -1)
+    {
+      for (i = O0_REGNUM; i <= O7_REGNUM; i++)
+       {
+         if (regno == i || regno == -1)
+           regcache_collect (i, regs + REG32_OFFSET_OUT +
+                             ((i - O0_REGNUM) * 4));
+        }
+    }
+
+  /* Responsibility for the stack regs is pushed off onto the caller.  */
+}
+
+void
+sparcnbsd_fill_reg64 (char *regs, int regno)
+{
+  int i;
+
+  if (regno == TSTATE_REGNUM || regno == -1)
+    regcache_collect (TSTATE_REGNUM, regs + REG64_OFFSET_TSTATE);
+
+  if (regno == PC_REGNUM || regno == -1)
+    regcache_collect (PC_REGNUM, regs + REG64_OFFSET_PC);
+
+  if (regno == NPC_REGNUM || regno == -1)
+    regcache_collect (NPC_REGNUM, regs + REG64_OFFSET_NPC);
+
+  if (regno == Y_REGNUM || regno == -1)
+    regcache_collect (Y_REGNUM, regs + REG64_OFFSET_Y);
+
+  if ((regno >= G0_REGNUM && regno <= G7_REGNUM) || regno == -1)
+    {
+      /* %g0 is always zero */
+      for (i = G1_REGNUM; i <= G7_REGNUM; i++)
+       {
+         if (regno == i || regno == -1)
+           regcache_collect (i, regs + REG64_OFFSET_GLOBAL +
+                             ((i - G0_REGNUM) * 4));
+       }
+    }
+
+  if ((regno >= O0_REGNUM && regno <= O7_REGNUM) || regno == -1)
+    {
+      for (i = O0_REGNUM; i <= O7_REGNUM; i++)
+       {
+         if (regno == i || regno == -1)
+           regcache_collect (i, regs + REG64_OFFSET_OUT +
+                             ((i - O0_REGNUM) * 4));
+        }
+    }
+
+  /* Responsibility for the stack regs is pushed off onto the caller.  */
+}
+
+void
+sparcnbsd_supply_fpreg32 (char *fpregs, int regno)
+{
+  int i;
+
+  for (i = 0; i <= 31; i++)
+    {
+      if (regno == (FP0_REGNUM + i) || regno == -1)
+       supply_register (FP0_REGNUM + i, fpregs + (i * 4));
+    }
+
+  if (regno == FPS_REGNUM || regno == -1)
+    supply_register (FPS_REGNUM, fpregs + (32 * 4));
+}
+
+void
+sparcnbsd_supply_fpreg64 (char *fpregs, int regno)
+{
+  int i;
+
+  for (i = 0; i <= 31; i++)
+    {
+      if (regno == (FP0_REGNUM + i) || regno == -1)
+       supply_register (FP0_REGNUM + i, fpregs + (i * 4));
+    }
+
+  for (; i <= 47; i++)
+    {
+      if (regno == (FP0_REGNUM + i) || regno == -1)
+       supply_register (FP0_REGNUM + i, fpregs + (32 * 4) + (i * 8));
+    }
+
+  if (regno == FPS_REGNUM || regno == -1)
+    supply_register (FPS_REGNUM, fpregs + (32 * 4) + (16 * 8));
+
+  /* XXX %gsr */
+}
+
+void
+sparcnbsd_fill_fpreg32 (char *fpregs, int regno)
+{
+  int i;
+
+  for (i = 0; i <= 31; i++)
+    {
+      if (regno == (FP0_REGNUM + i) || regno == -1)
+       regcache_collect (FP0_REGNUM + i, fpregs + (i * 4));
+    }
+
+  if (regno == FPS_REGNUM || regno == -1)
+    regcache_collect (FPS_REGNUM, fpregs + (32 * 4));
+}
+
+void
+sparcnbsd_fill_fpreg64 (char *fpregs, int regno)
+{
+  int i;
+
+  for (i = 0; i <= 31; i++)
+    {
+      if (regno == (FP0_REGNUM + i) || regno == -1)
+       regcache_collect (FP0_REGNUM + i, fpregs + (i * 4));
+    }
+
+  for (; i <= 47; i++)
+    {
+      if (regno == (FP0_REGNUM + i) || regno == -1)
+       regcache_collect (FP0_REGNUM + i, fpregs + (32 * 4) + (i * 8));
+    }
+
+  if (regno == FPS_REGNUM || regno == -1)
+    regcache_collect (FPS_REGNUM, fpregs + (32 * 4) + (16 * 8));
+
+  /* XXX %gsr */
+}
+
+/* Unlike other NetBSD implementations, the SPARC port historically used
+   .reg and .reg2 (see bfd/netbsd-core.c), and as such, we can share one
+   routine for a.out and ELF core files.  */
+static void
+fetch_core_registers (char *core_reg_sect, unsigned core_reg_size, int which,
+                      CORE_ADDR ignore)
+{
+  int reg_size, fpreg_size;
+
+  if (gdbarch_ptr_bit (current_gdbarch) == 32)
+    {
+      reg_size = (20 * 4);
+      fpreg_size = (33 * 4);
+    }
+  else
+    {
+      reg_size = (20 * 8);
+      fpreg_size = (64 * 4)
+        + 8  /* fsr */
+        + 4  /* gsr */
+        + 4; /* pad */
+    }
+
+  switch (which)
+    {
+    case 0:  /* Integer registers */
+      if (core_reg_size != reg_size)
+       warning ("Wrong size register set in core file.");
+      else if (gdbarch_ptr_bit (current_gdbarch) == 32)
+       sparcnbsd_supply_reg32 (core_reg_sect, -1);
+      else
+       sparcnbsd_supply_reg64 (core_reg_sect, -1);
+      break;
+
+    case 2:  /* Floating pointer registers */
+      if (core_reg_size != fpreg_size)
+       warning ("Wrong size FP register set in core file.");
+      else if (gdbarch_ptr_bit (current_gdbarch) == 32)
+       sparcnbsd_supply_fpreg32 (core_reg_sect, -1);
+      else
+       sparcnbsd_supply_fpreg64 (core_reg_sect, -1);
+      break;
+
+    default:
+      /* Don't know what kind of register request this is; just ignore it.  */
+      break;
+    }
+}
+
+static struct core_fns sparcnbsd_core_fns =
+{
+  bfd_target_unknown_flavour,          /* core_flavour */
+  default_check_format,                        /* check_format */
+  default_core_sniffer,                        /* core_sniffer */
+  fetch_core_registers,                        /* core_read_registers */
+  NULL
+};
+
+static struct core_fns sparcnbsd_elfcore_fns =
+{
+  bfd_target_elf_flavour,              /* core_flavour */
+  default_check_format,                        /* check_format */
+  default_core_sniffer,                        /* core_sniffer */
+  fetch_core_registers,                        /* core_read_registers */
+  NULL
+};
+
+/* FIXME: Need PC_IN_SIGTRAMP() support, but NetBSD/sparc signal trampolines
+   aren't easily identified.  */
+
+static int
+sparcnbsd_get_longjmp_target_32 (CORE_ADDR *pc)
+{
+  CORE_ADDR jb_addr;
+  char buf[4];
+
+  jb_addr = read_register (O0_REGNUM);
+
+  if (target_read_memory (jb_addr + 12, buf, sizeof (buf)))
+    return 0;
+
+  *pc = extract_address (buf, sizeof (buf));
+
+  return 1;
+}
+
+static int
+sparcnbsd_get_longjmp_target_64 (CORE_ADDR *pc)
+{
+  CORE_ADDR jb_addr;
+  char buf[8];
+
+  jb_addr = read_register (O0_REGNUM);
+
+  if (target_read_memory (jb_addr + 16, buf, sizeof (buf)))
+    return 0;
+
+  *pc = extract_address (buf, sizeof (buf));
+
+  return 1;
+}
+
+static int
+sparcnbsd_aout_in_solib_call_trampoline (CORE_ADDR pc, char *name)
+{
+  if (strcmp (name, "_DYNAMIC") == 0)
+    return 1;
+
+  return 0;
+}
+
+static void
+sparcnbsd_init_abi_common (struct gdbarch_info info,
+                           struct gdbarch *gdbarch)
+{
+  set_gdbarch_get_longjmp_target (gdbarch, gdbarch_ptr_bit (gdbarch) == 32 ?
+                                          sparcnbsd_get_longjmp_target_32 :
+                                          sparcnbsd_get_longjmp_target_64);
+}
+
+static void
+sparcnbsd_init_abi_aout (struct gdbarch_info info,
+                         struct gdbarch *gdbarch)
+{
+  sparcnbsd_init_abi_common (info, gdbarch);
+
+  set_gdbarch_in_solib_call_trampoline (gdbarch,
+                                     sparcnbsd_aout_in_solib_call_trampoline);
+}
+
+static void
+sparcnbsd_init_abi_elf (struct gdbarch_info info,
+                        struct gdbarch *gdbarch)
+{
+  sparcnbsd_init_abi_common (info, gdbarch);
+
+  set_solib_svr4_fetch_link_map_offsets (gdbarch,
+                                        gdbarch_ptr_bit (gdbarch) == 32 ?
+                                nbsd_ilp32_solib_svr4_fetch_link_map_offsets :
+                               nbsd_lp64_solib_svr4_fetch_link_map_offsets);
+}
+
+static enum gdb_osabi
+sparcnbsd_aout_osabi_sniffer (bfd *abfd)
+{
+  if (strcmp (bfd_get_target (abfd), "a.out-sparc-netbsd") == 0)
+    return GDB_OSABI_NETBSD_AOUT;
+
+  return GDB_OSABI_UNKNOWN;
+}
+
+void
+_initialize_sparnbsd_tdep (void)
+{
+  gdbarch_register_osabi_sniffer (bfd_arch_sparc, bfd_target_aout_flavour,
+                                 sparcnbsd_aout_osabi_sniffer);
+
+  gdbarch_register_osabi (bfd_arch_sparc, GDB_OSABI_NETBSD_AOUT,
+                         sparcnbsd_init_abi_aout);
+  gdbarch_register_osabi (bfd_arch_sparc, GDB_OSABI_NETBSD_ELF,
+                         sparcnbsd_init_abi_elf);
+
+  add_core_fns (&sparcnbsd_core_fns);
+  add_core_fns (&sparcnbsd_elfcore_fns);
+}
diff --git a/gdb/sparcnbsd-tdep.h b/gdb/sparcnbsd-tdep.h
new file mode 100644 (file)
index 0000000..bad2d65
--- /dev/null
@@ -0,0 +1,34 @@
+/* Common target dependent code for GDB on SPARC systems running NetBSD.
+   Copyright 2002 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., 59 Temple Place - Suite 330,
+   Boston, MA 02111-1307, USA.  */
+
+#ifndef SPARCNBSD_TDEP_H
+#define SPARCNBSD_TDEP_H
+
+void sparcnbsd_supply_reg32 (char *, int);
+void sparcnbsd_supply_reg64 (char *, int);
+void sparcnbsd_fill_reg32 (char *, int);
+void sparcnbsd_fill_reg64 (char *, int);
+
+void sparcnbsd_supply_fpreg32 (char *, int);
+void sparcnbsd_supply_fpreg64 (char *, int);
+void sparcnbsd_fill_fpreg32 (char *, int);
+void sparcnbsd_fill_fpreg64 (char *, int);
+
+#endif /* SPARCNBSD_TDEP_H */