GDB (xrefs)
/tmp/gdb-7.10/gdb/m68kbsd-nat.c
Go to the documentation of this file.
1 /* Native-dependent code for Motorola 68000 BSD's.
2 
3  Copyright (C) 2004-2015 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 3 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, see <http://www.gnu.org/licenses/>. */
19 
20 #include "defs.h"
21 #include "gdbcore.h"
22 #include "inferior.h"
23 #include "regcache.h"
24 
25 #include <sys/types.h>
26 #include <sys/ptrace.h>
27 #include <machine/reg.h>
28 
29 #include "m68k-tdep.h"
30 #include "inf-ptrace.h"
31 
32 static int
34 {
35  return (regnum >= M68K_D0_REGNUM && regnum <= M68K_PC_REGNUM);
36 }
37 
38 static int
40 {
41  return (regnum >= M68K_FP0_REGNUM && regnum <= M68K_FPI_REGNUM);
42 }
43 
44 /* Supply the general-purpose registers stored in GREGS to REGCACHE. */
45 
46 static void
47 m68kbsd_supply_gregset (struct regcache *regcache, const void *gregs)
48 {
49  const char *regs = gregs;
50  int regnum;
51 
52  for (regnum = M68K_D0_REGNUM; regnum <= M68K_PC_REGNUM; regnum++)
53  regcache_raw_supply (regcache, regnum, regs + regnum * 4);
54 }
55 
56 /* Supply the floating-point registers stored in FPREGS to REGCACHE. */
57 
58 static void
59 m68kbsd_supply_fpregset (struct regcache *regcache, const void *fpregs)
60 {
61  struct gdbarch *gdbarch = get_regcache_arch (regcache);
62  const char *regs = fpregs;
63  int regnum;
64 
65  for (regnum = M68K_FP0_REGNUM; regnum <= M68K_FPI_REGNUM; regnum++)
66  regcache_raw_supply (regcache, regnum,
67  regs + m68kbsd_fpreg_offset (gdbarch, regnum));
68 }
69 
70 /* Collect the general-purpose registers from REGCACHE and store them
71  in GREGS. */
72 
73 static void
75  void *gregs, int regnum)
76 {
77  char *regs = gregs;
78  int i;
79 
80  for (i = M68K_D0_REGNUM; i <= M68K_PC_REGNUM; i++)
81  {
82  if (regnum == -1 || regnum == i)
83  regcache_raw_collect (regcache, i, regs + i * 4);
84  }
85 }
86 
87 /* Collect the floating-point registers from REGCACHE and store them
88  in FPREGS. */
89 
90 static void
92  void *fpregs, int regnum)
93 {
94  struct gdbarch *gdbarch = get_regcache_arch (regcache);
95  char *regs = fpregs;
96  int i;
97 
98  for (i = M68K_FP0_REGNUM; i <= M68K_FPI_REGNUM; i++)
99  {
100  if (regnum == -1 || regnum == i)
101  regcache_raw_collect (regcache, i,
102  regs + m68kbsd_fpreg_offset (gdbarch, i));
103  }
104 }
105 
106 
107 /* Fetch register REGNUM from the inferior. If REGNUM is -1, do this
108  for all registers (including the floating-point registers). */
109 
110 static void
112  struct regcache *regcache, int regnum)
113 {
114  if (regnum == -1 || m68kbsd_gregset_supplies_p (regnum))
115  {
116  struct reg regs;
117 
118  if (ptrace (PT_GETREGS, ptid_get_pid (inferior_ptid),
119  (PTRACE_TYPE_ARG3) &regs, 0) == -1)
120  perror_with_name (_("Couldn't get registers"));
121 
122  m68kbsd_supply_gregset (regcache, &regs);
123  }
124 
125  if (regnum == -1 || m68kbsd_fpregset_supplies_p (regnum))
126  {
127  struct fpreg fpregs;
128 
129  if (ptrace (PT_GETFPREGS, ptid_get_pid (inferior_ptid),
130  (PTRACE_TYPE_ARG3) &fpregs, 0) == -1)
131  perror_with_name (_("Couldn't get floating point status"));
132 
133  m68kbsd_supply_fpregset (regcache, &fpregs);
134  }
135 }
136 
137 /* Store register REGNUM back into the inferior. If REGNUM is -1, do
138  this for all registers (including the floating-point registers). */
139 
140 static void
142  struct regcache *regcache, int regnum)
143 {
144  if (regnum == -1 || m68kbsd_gregset_supplies_p (regnum))
145  {
146  struct reg regs;
147 
148  if (ptrace (PT_GETREGS, ptid_get_pid (inferior_ptid),
149  (PTRACE_TYPE_ARG3) &regs, 0) == -1)
150  perror_with_name (_("Couldn't get registers"));
151 
152  m68kbsd_collect_gregset (regcache, &regs, regnum);
153 
154  if (ptrace (PT_SETREGS, ptid_get_pid (inferior_ptid),
155  (PTRACE_TYPE_ARG3) &regs, 0) == -1)
156  perror_with_name (_("Couldn't write registers"));
157  }
158 
159  if (regnum == -1 || m68kbsd_fpregset_supplies_p (regnum))
160  {
161  struct fpreg fpregs;
162 
163  if (ptrace (PT_GETFPREGS, ptid_get_pid (inferior_ptid),
164  (PTRACE_TYPE_ARG3) &fpregs, 0) == -1)
165  perror_with_name (_("Couldn't get floating point status"));
166 
167  m68kbsd_collect_fpregset (regcache, &fpregs, regnum);
168 
169  if (ptrace (PT_SETFPREGS, ptid_get_pid (inferior_ptid),
170  (PTRACE_TYPE_ARG3) &fpregs, 0) == -1)
171  perror_with_name (_("Couldn't write floating point status"));
172  }
173 }
174 
175 
176 /* Support for debugging kernel virtual memory images. */
177 
178 #include <machine/pcb.h>
179 
180 #include "bsd-kvm.h"
181 
182 /* OpenBSD doesn't have these. */
183 #ifndef PCB_REGS_FP
184 #define PCB_REGS_FP 10
185 #endif
186 #ifndef PCB_REGS_SP
187 #define PCB_REGS_SP 11
188 #endif
189 
190 static int
191 m68kbsd_supply_pcb (struct regcache *regcache, struct pcb *pcb)
192 {
193  int regnum, tmp;
194  int i = 0;
195 
196  /* The following is true for NetBSD 1.6.2:
197 
198  The pcb contains %d2...%d7, %a2...%a7 and %ps. This accounts for
199  all callee-saved registers. From this information we reconstruct
200  the register state as it would look when we just returned from
201  cpu_switch(). */
202 
203  /* The stack pointer shouldn't be zero. */
204  if (pcb->pcb_regs[PCB_REGS_SP] == 0)
205  return 0;
206 
207  for (regnum = M68K_D2_REGNUM; regnum <= M68K_D7_REGNUM; regnum++)
208  regcache_raw_supply (regcache, regnum, &pcb->pcb_regs[i++]);
209  for (regnum = M68K_A2_REGNUM; regnum <= M68K_SP_REGNUM; regnum++)
210  regcache_raw_supply (regcache, regnum, &pcb->pcb_regs[i++]);
211 
212  tmp = pcb->pcb_ps & 0xffff;
213  regcache_raw_supply (regcache, M68K_PS_REGNUM, &tmp);
214 
215  read_memory (pcb->pcb_regs[PCB_REGS_FP] + 4, (char *) &tmp, sizeof tmp);
216  regcache_raw_supply (regcache, M68K_PC_REGNUM, &tmp);
217 
218  return 1;
219 }
220 
221 
222 /* Provide a prototype to silence -Wmissing-prototypes. */
223 void _initialize_m68kbsd_nat (void);
224 
225 void
227 {
228  struct target_ops *t;
229 
230  t = inf_ptrace_target ();
233  add_target (t);
234 
235  /* Support debugging kernel virtual memory images. */
237 }
void add_target(struct target_ops *t)
Definition: target.c:395
struct gdbarch * get_regcache_arch(const struct regcache *regcache)
Definition: regcache.c:297
int m68kbsd_fpreg_offset(struct gdbarch *gdbarch, int regnum)
Definition: m68kbsd-tdep.c:42
static int m68kbsd_fpregset_supplies_p(int regnum)
Definition: m68kbsd-nat.c:39
void _initialize_m68kbsd_nat(void)
Definition: m68kbsd-nat.c:226
#define _(String)
Definition: gdb_locale.h:40
struct target_ops * inf_ptrace_target(void)
Definition: inf-ptrace.c:668
PTRACE_TYPE_RET ptrace()
static int m68kbsd_gregset_supplies_p(int regnum)
Definition: m68kbsd-nat.c:33
static void m68kbsd_fetch_inferior_registers(struct target_ops *ops, struct regcache *regcache, int regnum)
Definition: m68kbsd-nat.c:111
static void m68kbsd_supply_gregset(struct regcache *regcache, const void *gregs)
Definition: m68kbsd-nat.c:47
int regnum
Definition: aarch64-tdep.c:69
void read_memory(CORE_ADDR memaddr, gdb_byte *myaddr, ssize_t len)
Definition: corefile.c:244
static void m68kbsd_collect_fpregset(struct regcache *regcache, void *fpregs, int regnum)
Definition: m68kbsd-nat.c:91
Definition: regdef.h:22
int ptid_get_pid(ptid_t ptid)
Definition: ptid.c:52
#define PCB_REGS_SP
Definition: m68kbsd-nat.c:187
void(* to_fetch_registers)(struct target_ops *, struct regcache *, int) TARGET_DEFAULT_IGNORE()
Definition: target.h:472
static void m68kbsd_store_inferior_registers(struct target_ops *ops, struct regcache *regcache, int regnum)
Definition: m68kbsd-nat.c:141
void void void void void void void void void perror_with_name(const char *string) ATTRIBUTE_NORETURN
Definition: utils.c:979
static void m68kbsd_collect_gregset(const struct regcache *regcache, void *gregs, int regnum)
Definition: m68kbsd-nat.c:74
ptid_t inferior_ptid
Definition: infcmd.c:124
static void m68kbsd_supply_fpregset(struct regcache *regcache, const void *fpregs)
Definition: m68kbsd-nat.c:59
void regcache_raw_supply(struct regcache *regcache, int regnum, const void *buf)
Definition: regcache.c:1041
void regcache_raw_collect(const struct regcache *regcache, int regnum, void *buf)
Definition: regcache.c:1071
#define PTRACE_TYPE_ARG3
Definition: config.h:658
void bsd_kvm_add_target(int(*supply_pcb)(struct regcache *, struct pcb *))
Definition: bsd-kvm.c:351
static int m68kbsd_supply_pcb(struct regcache *regcache, struct pcb *pcb)
Definition: m68kbsd-nat.c:191
#define PCB_REGS_FP
Definition: m68kbsd-nat.c:184
void(* to_store_registers)(struct target_ops *, struct regcache *, int) TARGET_DEFAULT_NORETURN(noprocess())
Definition: target.h:474