bsd-kvm.c revision 1.5
1/* BSD Kernel Data Access Library (libkvm) interface.
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#define _KMEMUSER
21#include "defs.h"
22#include "cli/cli-cmds.h"
23#include "command.h"
24#include "frame.h"
25#include "regcache.h"
26#include "target.h"
27#include "value.h"
28#include "gdbcore.h"		/* for get_exec_file */
29#include "gdbthread.h"
30
31#include <fcntl.h>
32#include <kvm.h>
33#ifdef HAVE_NLIST_H
34#include <nlist.h>
35#endif
36#include <paths.h>
37#include "readline/readline.h"
38#include <sys/param.h>
39#include <sys/proc.h>
40#include <sys/user.h>
41
42#include "bsd-kvm.h"
43
44/* Kernel memory device file.  */
45static const char *bsd_kvm_corefile;
46
47/* Kernel memory interface descriptor.  */
48static kvm_t *core_kd;
49
50/* Address of process control block.  */
51static struct pcb *bsd_kvm_paddr;
52
53/* Pointer to architecture-specific function that reconstructs the
54   register state from PCB and supplies it to REGCACHE.  */
55static int (*bsd_kvm_supply_pcb)(struct regcache *regcache, struct pcb *pcb);
56
57/* Target ops for libkvm interface.  */
58static struct target_ops bsd_kvm_ops;
59
60/* This is the ptid we use while we're connected to kvm.  The kvm
61   target currently doesn't export any view of the running processes,
62   so this represents the kernel task.  */
63static ptid_t bsd_kvm_ptid;
64
65static void
66bsd_kvm_open (const char *arg, int from_tty)
67{
68  char errbuf[_POSIX2_LINE_MAX];
69  char *execfile = NULL;
70  kvm_t *temp_kd;
71  struct inferior *inf;
72  char *filename = NULL;
73
74  target_preopen (from_tty);
75
76  if (arg)
77    {
78      char *temp;
79
80      filename = tilde_expand (arg);
81      if (filename[0] != '/')
82	{
83	  temp = concat (current_directory, "/", filename, (char *)NULL);
84	  xfree (filename);
85	  filename = temp;
86	}
87    }
88
89  execfile = get_exec_file (0);
90  temp_kd = kvm_openfiles (execfile, filename, NULL,
91			   write_files ? O_RDWR : O_RDONLY, errbuf);
92  if (temp_kd == NULL)
93    error (("%s"), errbuf);
94
95  bsd_kvm_corefile = filename;
96  unpush_target (&bsd_kvm_ops);
97  core_kd = temp_kd;
98  push_target (&bsd_kvm_ops);
99
100  inf = add_inferior_silent (ptid_get_pid(bsd_kvm_ptid));
101  inf->aspace = maybe_new_address_space ();
102  inf->pspace = add_program_space (inf->aspace);
103
104  add_thread_silent (bsd_kvm_ptid);
105  inferior_ptid = bsd_kvm_ptid;
106
107  target_fetch_registers (get_current_regcache (), -1);
108
109  reinit_frame_cache ();
110  print_stack_frame (get_selected_frame (NULL), 0, SRC_AND_LOC, 1);
111}
112
113static void
114bsd_kvm_close (struct target_ops *self)
115{
116  if (core_kd)
117    {
118      if (kvm_close (core_kd) == -1)
119	warning (("%s"), kvm_geterr(core_kd));
120      core_kd = NULL;
121    }
122
123  inferior_ptid = null_ptid;
124  delete_thread_silent (bsd_kvm_ptid);
125}
126
127static LONGEST
128bsd_kvm_xfer_memory (CORE_ADDR addr, ULONGEST len,
129		     gdb_byte *readbuf, const gdb_byte *writebuf)
130{
131  ssize_t nbytes = len;
132
133  if (readbuf)
134    nbytes = kvm_read (core_kd, addr, readbuf, nbytes);
135  if (writebuf && nbytes > 0)
136    nbytes = kvm_write (core_kd, addr, writebuf, nbytes);
137  return nbytes;
138}
139
140static enum target_xfer_status
141bsd_kvm_xfer_partial (struct target_ops *ops, enum target_object object,
142		      const char *annex, gdb_byte *readbuf,
143		      const gdb_byte *writebuf,
144		      ULONGEST offset, ULONGEST len, ULONGEST *xfered_len)
145{
146  switch (object)
147    {
148    case TARGET_OBJECT_MEMORY:
149      {
150	LONGEST ret = bsd_kvm_xfer_memory (offset, len, readbuf, writebuf);
151
152	if (ret < 0)
153	  return TARGET_XFER_E_IO;
154	else if (ret == 0)
155	  return TARGET_XFER_EOF;
156	else
157	  {
158	    *xfered_len = (ULONGEST) ret;
159	    return TARGET_XFER_OK;
160	  }
161      }
162
163    default:
164      return TARGET_XFER_E_IO;
165    }
166}
167
168static void
169bsd_kvm_files_info (struct target_ops *ops)
170{
171  if (bsd_kvm_corefile && strcmp (bsd_kvm_corefile, _PATH_MEM) != 0)
172    printf_filtered (_("\tUsing the kernel crash dump %s.\n"),
173		     bsd_kvm_corefile);
174  else
175    printf_filtered (_("\tUsing the currently running kernel.\n"));
176}
177
178/* Fetch process control block at address PADDR.  */
179
180static int
181bsd_kvm_fetch_pcb (struct regcache *regcache, struct pcb *paddr)
182{
183  struct pcb pcb;
184
185  if (kvm_read (core_kd, (unsigned long) paddr, &pcb, sizeof pcb) == -1)
186    error (("%s"), kvm_geterr (core_kd));
187
188  gdb_assert (bsd_kvm_supply_pcb);
189  return bsd_kvm_supply_pcb (regcache, &pcb);
190}
191
192static void
193bsd_kvm_fetch_registers (struct target_ops *ops,
194			 struct regcache *regcache, int regnum)
195{
196  struct nlist nl[2];
197
198  if (bsd_kvm_paddr)
199    {
200      bsd_kvm_fetch_pcb (regcache, bsd_kvm_paddr);
201      return;
202    }
203
204  /* On dumping core, BSD kernels store the faulting context (PCB)
205     in the variable "dumppcb".  */
206  memset (nl, 0, sizeof nl);
207  nl[0].n_name = "_dumppcb";
208
209  if (kvm_nlist (core_kd, nl) == -1)
210    error (("%s"), kvm_geterr (core_kd));
211
212  if (nl[0].n_value != 0)
213    {
214      /* Found dumppcb.  If it contains a valid context, return
215	 immediately.  */
216      if (bsd_kvm_fetch_pcb (regcache, (struct pcb *) nl[0].n_value))
217	return;
218    }
219
220  /* Traditional BSD kernels have a process proc0 that should always
221     be present.  The address of proc0's PCB is stored in the variable
222     "proc0paddr".  */
223
224  memset (nl, 0, sizeof nl);
225  nl[0].n_name = "_proc0paddr";
226
227  if (kvm_nlist (core_kd, nl) == -1)
228    error (("%s"), kvm_geterr (core_kd));
229
230  if (nl[0].n_value != 0)
231    {
232      struct pcb *paddr;
233
234      /* Found proc0paddr.  */
235      if (kvm_read (core_kd, nl[0].n_value, &paddr, sizeof paddr) == -1)
236	error (("%s"), kvm_geterr (core_kd));
237
238      bsd_kvm_fetch_pcb (regcache, paddr);
239      return;
240    }
241
242#if 1 /* TODO: HAVE_STRUCT_LWP_L_ADDR */
243  memset (nl, 0, sizeof nl);
244  nl[0].n_name = "_lwp0";
245
246  if (kvm_nlist (core_kd, nl) == -1)
247    error (("%s"), kvm_geterr (core_kd));
248
249  if (nl[0].n_value != 0)
250    {
251      struct pcb *paddr;
252
253      /* Found lwp0.  */
254      nl[0].n_value += offsetof (struct lwp, l_addr);
255      if (kvm_read (core_kd, nl[0].n_value, &paddr, sizeof paddr) == -1)
256	error (("%s"), kvm_geterr (core_kd));
257
258      bsd_kvm_fetch_pcb (regcache, paddr);
259      return;
260    }
261#endif
262
263#ifdef HAVE_STRUCT_THREAD_TD_PCB
264  /* In FreeBSD kernels for 5.0-RELEASE and later, the PCB no longer
265     lives in `struct proc' but in `struct thread'.  The `struct
266     thread' for the initial thread for proc0 can be found in the
267     variable "thread0".  */
268
269  memset (nl, 0, sizeof nl);
270  nl[0].n_name = "_thread0";
271
272  if (kvm_nlist (core_kd, nl) == -1)
273    error (("%s"), kvm_geterr (core_kd));
274
275  if (nl[0].n_value != 0)
276    {
277      struct pcb *paddr;
278
279      /* Found thread0.  */
280      nl[0].n_value += offsetof (struct thread, td_pcb);
281      if (kvm_read (core_kd, nl[0].n_value, &paddr, sizeof paddr) == -1)
282	error (("%s"), kvm_geterr (core_kd));
283
284      bsd_kvm_fetch_pcb (regcache, paddr);
285      return;
286    }
287#endif
288
289  /* i18n: PCB == "Process Control Block".  */
290  error (_("Cannot find a valid PCB"));
291}
292
293
294/* Kernel memory interface commands.  */
295struct cmd_list_element *bsd_kvm_cmdlist;
296
297static void
298bsd_kvm_cmd (char *arg, int fromtty)
299{
300  /* ??? Should this become an alias for "target kvm"?  */
301}
302
303#ifndef HAVE_STRUCT_THREAD_TD_PCB
304
305static void
306bsd_kvm_proc_cmd (char *arg, int fromtty)
307{
308  CORE_ADDR addr;
309
310  if (arg == NULL)
311    error_no_arg (_("proc address"));
312
313  if (core_kd == NULL)
314    error (_("No kernel memory image."));
315
316  addr = parse_and_eval_address (arg);
317#ifdef HAVE_STRUCT_LWP
318  addr += offsetof (struct lwp, l_addr);
319#else
320  addr += offsetof (struct proc, p_addr);
321#endif
322
323  if (kvm_read (core_kd, addr, &bsd_kvm_paddr, sizeof bsd_kvm_paddr) == -1)
324    error (("%s"), kvm_geterr (core_kd));
325
326  target_fetch_registers (get_current_regcache (), -1);
327
328  reinit_frame_cache ();
329  print_stack_frame (get_selected_frame (NULL), 0, SRC_AND_LOC, 1);
330}
331
332#endif
333
334static void
335bsd_kvm_pcb_cmd (char *arg, int fromtty)
336{
337  if (arg == NULL)
338    /* i18n: PCB == "Process Control Block".  */
339    error_no_arg (_("pcb address"));
340
341  if (core_kd == NULL)
342    error (_("No kernel memory image."));
343
344  bsd_kvm_paddr = (struct pcb *)(u_long) parse_and_eval_address (arg);
345
346  target_fetch_registers (get_current_regcache (), -1);
347
348  reinit_frame_cache ();
349  print_stack_frame (get_selected_frame (NULL), 0, SRC_AND_LOC, 1);
350}
351
352static int
353bsd_kvm_thread_alive (struct target_ops *ops,
354		      ptid_t ptid)
355{
356  return 1;
357}
358
359static char *
360bsd_kvm_pid_to_str (struct target_ops *ops, ptid_t ptid)
361{
362  static char buf[64];
363  xsnprintf (buf, sizeof buf, "<kvm>");
364  return buf;
365}
366
367static int
368bsd_kvm_return_one (struct target_ops *ops)
369{
370  return 1;
371}
372
373/* Add the libkvm interface to the list of all possible targets and
374   register CUPPLY_PCB as the architecture-specific process control
375   block interpreter.  */
376
377void
378bsd_kvm_add_target (int (*supply_pcb)(struct regcache *, struct pcb *))
379{
380  gdb_assert (bsd_kvm_supply_pcb == NULL);
381  bsd_kvm_supply_pcb = supply_pcb;
382
383  bsd_kvm_ops.to_shortname = "kvm";
384  bsd_kvm_ops.to_longname = _("Kernel memory interface");
385  bsd_kvm_ops.to_doc = _("Use a kernel virtual memory image as a target.\n\
386Optionally specify the filename of a core dump.");
387  bsd_kvm_ops.to_open = bsd_kvm_open;
388  bsd_kvm_ops.to_close = bsd_kvm_close;
389  bsd_kvm_ops.to_fetch_registers = bsd_kvm_fetch_registers;
390  bsd_kvm_ops.to_xfer_partial = bsd_kvm_xfer_partial;
391  bsd_kvm_ops.to_files_info = bsd_kvm_files_info;
392  bsd_kvm_ops.to_thread_alive = bsd_kvm_thread_alive;
393  bsd_kvm_ops.to_pid_to_str = bsd_kvm_pid_to_str;
394  bsd_kvm_ops.to_stratum = process_stratum;
395  bsd_kvm_ops.to_has_memory = bsd_kvm_return_one;
396  bsd_kvm_ops.to_has_stack = bsd_kvm_return_one;
397  bsd_kvm_ops.to_has_registers = bsd_kvm_return_one;
398  bsd_kvm_ops.to_magic = OPS_MAGIC;
399
400  add_target (&bsd_kvm_ops);
401
402  add_prefix_cmd ("kvm", class_obscure, bsd_kvm_cmd, _("\
403Generic command for manipulating the kernel memory interface."),
404		  &bsd_kvm_cmdlist, "kvm ", 0, &cmdlist);
405
406#ifndef HAVE_STRUCT_THREAD_TD_PCB
407  add_cmd ("proc", class_obscure, bsd_kvm_proc_cmd,
408	   _("Set current context from proc address"), &bsd_kvm_cmdlist);
409#endif
410  add_cmd ("pcb", class_obscure, bsd_kvm_pcb_cmd,
411	   /* i18n: PCB == "Process Control Block".  */
412	   _("Set current context from pcb address"), &bsd_kvm_cmdlist);
413
414  /* Some notes on the ptid usage on this target.
415
416     The pid field represents the kvm inferior instance.  Currently,
417     we don't support multiple kvm inferiors, but we start at 1
418     anyway.  The lwp field is set to != 0, in case the core wants to
419     refer to the whole kvm inferior with ptid(1,0,0).
420
421     If kvm is made to export running processes as gdb threads,
422     the following form can be used:
423     ptid (1, 1, 0) -> kvm inferior 1, in kernel
424     ptid (1, 1, 1) -> kvm inferior 1, process 1
425     ptid (1, 1, 2) -> kvm inferior 1, process 2
426     ptid (1, 1, n) -> kvm inferior 1, process n  */
427
428  bsd_kvm_ptid = ptid_build (1, 1, 0);
429}
430