1 /* Native-dependent code for OpenBSD/sparc64.
2
3 Copyright 2003, 2004, 2006 Free Software Foundation, Inc.
4
5 This file is part of GDB.
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 59 Temple Place - Suite 330,
20 Boston, MA 02111-1307, USA. */
21
22 #include "defs.h"
23 #include "gdbcore.h"
24 #include "regcache.h"
25 #include "target.h"
26
27 #include "obsd-nat.h"
28 #include "sparc64-tdep.h"
29 #include "sparc-nat.h"
30
31 static void
sparc64obsd_supply_gregset(const struct sparc_gregset * gregset,struct regcache * regcache,int regnum,const void * gregs)32 sparc64obsd_supply_gregset (const struct sparc_gregset *gregset,
33 struct regcache *regcache,
34 int regnum, const void *gregs)
35 {
36 sparc64_supply_gregset (&sparc64nbsd_gregset, regcache, regnum, gregs);
37 }
38
39 static void
sparc64obsd_collect_gregset(const struct sparc_gregset * gregset,const struct regcache * regcache,int regnum,void * gregs)40 sparc64obsd_collect_gregset (const struct sparc_gregset *gregset,
41 const struct regcache *regcache,
42 int regnum, void *gregs)
43 {
44 sparc64_collect_gregset (&sparc64nbsd_gregset, regcache, regnum, gregs);
45 }
46
47 static void
sparc64obsd_supply_fpregset(struct regcache * regcache,int regnum,const void * fpregs)48 sparc64obsd_supply_fpregset (struct regcache *regcache,
49 int regnum, const void *fpregs)
50 {
51 sparc64_supply_fpregset (regcache, regnum, fpregs);
52 }
53
54 static void
sparc64obsd_collect_fpregset(const struct regcache * regcache,int regnum,void * fpregs)55 sparc64obsd_collect_fpregset (const struct regcache *regcache,
56 int regnum, void *fpregs)
57 {
58 sparc64_collect_fpregset (regcache, regnum, fpregs);
59 }
60
61 /* Determine whether `gregset_t' contains register REGNUM. */
62
63 static int
sparc64obsd_gregset_supplies_p(int regnum)64 sparc64obsd_gregset_supplies_p (int regnum)
65 {
66 /* Integer registers. */
67 if ((regnum >= SPARC_G1_REGNUM && regnum <= SPARC_G7_REGNUM)
68 || (regnum >= SPARC_O0_REGNUM && regnum <= SPARC_O7_REGNUM)
69 || (regnum >= SPARC_L0_REGNUM && regnum <= SPARC_L7_REGNUM)
70 || (regnum >= SPARC_I0_REGNUM && regnum <= SPARC_I7_REGNUM))
71 return 1;
72
73 /* Control registers. */
74 if (regnum == SPARC64_PC_REGNUM
75 || regnum == SPARC64_NPC_REGNUM
76 || regnum == SPARC64_STATE_REGNUM
77 || regnum == SPARC64_Y_REGNUM)
78 return 1;
79
80 return 0;
81 }
82
83 /* Determine whether `fpregset_t' contains register REGNUM. */
84
85 static int
sparc64obsd_fpregset_supplies_p(int regnum)86 sparc64obsd_fpregset_supplies_p (int regnum)
87 {
88 /* Floating-point registers. */
89 if ((regnum >= SPARC_F0_REGNUM && regnum <= SPARC_F31_REGNUM)
90 || (regnum >= SPARC64_F32_REGNUM && regnum <= SPARC64_F62_REGNUM))
91 return 1;
92
93 /* Control registers. */
94 if (regnum == SPARC64_FSR_REGNUM)
95 return 1;
96
97 return 0;
98 }
99
100
101 /* Support for debugging kernel virtual memory images. */
102
103 #include <sys/types.h>
104 #include <machine/pcb.h>
105
106 #include "bsd-kvm.h"
107
108 static int
sparc64obsd_supply_pcb(struct regcache * regcache,struct pcb * pcb)109 sparc64obsd_supply_pcb (struct regcache *regcache, struct pcb *pcb)
110 {
111 u_int64_t state;
112 int regnum;
113
114 /* The following is true for OpenBSD 3.0:
115
116 The pcb contains %sp and %pc, %pstate and %cwp. From this
117 information we reconstruct the register state as it would look
118 when we just returned from cpu_switch(). */
119
120 /* The stack pointer shouldn't be zero. */
121 if (pcb->pcb_sp == 0)
122 return 0;
123
124 /* If the program counter is zero, this is probably a core dump, and
125 we can get %pc from the stack. */
126 if (pcb->pcb_pc == 0)
127 read_memory(pcb->pcb_sp + BIAS - 176 + (11 * 8),
128 (char *)&pcb->pcb_pc, sizeof pcb->pcb_pc);
129
130 regcache_raw_supply (regcache, SPARC_SP_REGNUM, &pcb->pcb_sp);
131 regcache_raw_supply (regcache, SPARC64_PC_REGNUM, &pcb->pcb_pc);
132
133 state = pcb->pcb_pstate << 8 | pcb->pcb_cwp;
134 regcache_raw_supply (regcache, SPARC64_STATE_REGNUM, &state);
135
136 sparc_supply_rwindow (regcache, pcb->pcb_sp, -1);
137
138 return 1;
139 }
140
141
142 /* Provide a prototype to silence -Wmissing-prototypes. */
143 void _initialize_sparc64obsd_nat (void);
144
145 void
_initialize_sparc64obsd_nat(void)146 _initialize_sparc64obsd_nat (void)
147 {
148 struct target_ops *t;
149
150 sparc_supply_gregset = sparc64obsd_supply_gregset;
151 sparc_collect_gregset = sparc64obsd_collect_gregset;
152 sparc_supply_fpregset = sparc64obsd_supply_fpregset;
153 sparc_collect_fpregset = sparc64obsd_collect_fpregset;
154 sparc_gregset_supplies_p = sparc64obsd_gregset_supplies_p;
155 sparc_fpregset_supplies_p = sparc64obsd_fpregset_supplies_p;
156
157 /* Add some extra features to the generic SPARC target. */
158 t = sparc_target ();
159 t->to_pid_to_str = obsd_pid_to_str;
160 t->to_find_new_threads = obsd_find_new_threads;
161 t->to_wait = obsd_wait;
162 add_target (t);
163
164 /* Support debugging kernel virtual memory images. */
165 bsd_kvm_add_target (sparc64obsd_supply_pcb);
166 }
167