diff --git a/gnu/usr.bin/gdb/kgdb/Makefile b/gnu/usr.bin/gdb/kgdb/Makefile new file mode 100644 index 00000000000..561e22bc4f3 --- /dev/null +++ b/gnu/usr.bin/gdb/kgdb/Makefile @@ -0,0 +1,14 @@ +# $FreeBSD$ + +PROG= kgdb +SRCS= kthr.c main.c trgt.c trgt_${MACHINE_ARCH}.c +WARNS?= 2 + +BULIBS= ${OBJ_BU}/libbfd/libbfd.a ${OBJ_BU}/libopcodes/libopcodes.a \ + ${OBJ_BU}/libiberty/libiberty.a +GDBLIBS= ${OBJ_GDB}/libgdb/libgdb.a + +DPADD= ${GDBLIBS} ${BULIBS} ${LIBKVM} ${LIBM} ${LIBREADLINE} ${LIBTERMCAP} +LDADD= ${GDBLIBS} ${BULIBS} -lkvm -lm -lreadline -ltermcap + +.include diff --git a/gnu/usr.bin/gdb/kgdb/kgdb.1 b/gnu/usr.bin/gdb/kgdb/kgdb.1 new file mode 100644 index 00000000000..2ade68bcd84 --- /dev/null +++ b/gnu/usr.bin/gdb/kgdb/kgdb.1 @@ -0,0 +1,50 @@ +.\" Copyright (c) 2004 Marcel Moolenaar +.\" All rights reserved. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR +.\" IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES +.\" OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. +.\" IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, +.\" INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, +.\" BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +.\" LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED +.\" AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +.\" OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.Dd August 1, 2004 +.Os +.Dt KGDB 1 +.Sh NAME +.Nm kgdb +.Nd The kernel debugger +.Sh SYNOPSIS +.Nm +.Op Ar -v +.Op Ar -d crashdir +.Op Ar -n dumpnr +.Op Ar kernel [ Ar core ] +.Sh DESCRIPTION +The +.Nm +utility is a debugger based on +.Xr gdb 1 +that allows debugging of kernel core files. +.Sh SEE ALSO +.Xr gdb 1 +.Sh HISTORY +The +.Nm +utility first appeared in its current form in +.Fx 5.3 . diff --git a/gnu/usr.bin/gdb/kgdb/kgdb.h b/gnu/usr.bin/gdb/kgdb/kgdb.h new file mode 100644 index 00000000000..eb380326b6a --- /dev/null +++ b/gnu/usr.bin/gdb/kgdb/kgdb.h @@ -0,0 +1,55 @@ +/* + * Copyright (c) 2004 Marcel Moolenaar + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * $FreeBSD$ + */ + +#ifndef _KGDB_H_ +#define _KGDB_H_ + +extern kvm_t *kvm; +extern int verbose; + +struct kthr { + struct kthr *next; + uintptr_t kaddr; + uintptr_t kstack; + uintptr_t pcb; + int tid; +}; + +extern struct kthr *curkthr; + +void kgdb_target(void); +void kgdb_trgt_fetch_registers(int); +void kgdb_trgt_store_registers(int); + +struct kthr *kgdb_thr_first(void); +struct kthr *kgdb_thr_init(void); +struct kthr *kgdb_thr_lookup(int); +struct kthr *kgdb_thr_next(struct kthr *); +struct kthr *kgdb_thr_select(struct kthr *); + +#endif /* _KGDB_H_ */ diff --git a/gnu/usr.bin/gdb/kgdb/kthr.c b/gnu/usr.bin/gdb/kgdb/kthr.c new file mode 100644 index 00000000000..25f8d491933 --- /dev/null +++ b/gnu/usr.bin/gdb/kgdb/kthr.c @@ -0,0 +1,141 @@ +/* + * Copyright (c) 2004 Marcel Moolenaar + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include +__FBSDID("$FreeBSD$"); + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "kgdb.h" + +static uintptr_t dumppcb; +static int dumptid; + +static struct kthr *first; +struct kthr *curkthr; + +static uintptr_t +lookup(const char *sym) +{ + struct nlist nl[2]; + + nl[0].n_name = (char *)(uintptr_t)sym; + nl[1].n_name = NULL; + if (kvm_nlist(kvm, nl) != 0) { + warnx("kvm_nlist(%s): %s", sym, kvm_geterr(kvm)); + return (0); + } + return (nl[0].n_value); +} + +struct kthr * +kgdb_thr_first(void) +{ + return (first); +} + +struct kthr * +kgdb_thr_init(void) +{ + struct proc p; + struct thread td; + struct kthr *kt; + uintptr_t addr, paddr; + + addr = lookup("_allproc"); + if (addr == 0) + return (NULL); + kvm_read(kvm, addr, &paddr, sizeof(paddr)); + + dumppcb = lookup("_dumppcb"); + if (dumppcb == 0) + return (NULL); + + addr = lookup("_dumptid"); + if (addr != 0) + kvm_read(kvm, addr, &dumptid, sizeof(dumptid)); + else + dumptid = -1; + + while (paddr != 0) { + if (kvm_read(kvm, paddr, &p, sizeof(p)) != sizeof(p)) + warnx("kvm_read: %s", kvm_geterr(kvm)); + addr = (uintptr_t)TAILQ_FIRST(&p.p_threads); + while (addr != 0) { + if (kvm_read(kvm, addr, &td, sizeof(td)) != sizeof(td)) + warnx("kvm_read: %s", kvm_geterr(kvm)); + kt = malloc(sizeof(*kt)); + kt->next = first; + kt->kaddr = addr; + kt->pcb = (td.td_tid == dumptid) ? dumppcb : + (uintptr_t)td.td_pcb; + kt->kstack = td.td_kstack; + kt->tid = td.td_tid; + first = kt; + addr = (uintptr_t)TAILQ_NEXT(&td, td_plist); + } + paddr = (uintptr_t)LIST_NEXT(&p, p_list); + } + curkthr = kgdb_thr_lookup(dumptid); + if (curkthr == NULL) + curkthr = first; + return (first); +} + +struct kthr * +kgdb_thr_lookup(int tid) +{ + struct kthr *kt; + + kt = first; + while (kt != NULL && kt->tid != tid) + kt = kt->next; + return (kt); +} + +struct kthr * +kgdb_thr_next(struct kthr *kt) +{ + return (kt->next); +} + +struct kthr * +kgdb_thr_select(struct kthr *kt) +{ + struct kthr *pcur; + + pcur = curkthr; + curkthr = kt; + return (pcur); +} diff --git a/gnu/usr.bin/gdb/kgdb/main.c b/gnu/usr.bin/gdb/kgdb/main.c new file mode 100644 index 00000000000..6204c0b507a --- /dev/null +++ b/gnu/usr.bin/gdb/kgdb/main.c @@ -0,0 +1,288 @@ +/* + * Copyright (c) 2004 Marcel Moolenaar + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include +__FBSDID("$FreeBSD$"); + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/* libgdb stuff. */ +#include +#include +#include +#include +#include +#include +#include +#include + +extern void (*init_ui_hook)(char *); + +extern void symbol_file_add_main (char *args, int from_tty); + +#include "kgdb.h" + +kvm_t *kvm; + +static int dumpnr; +static int verbose; + +static char crashdir[PATH_MAX]; +static char *kernel; +static char *vmcore; + +static void (*kgdb_new_objfile_chain)(struct objfile * objfile); + +static void +usage(void) +{ + fprintf(stderr, + "usage: %s [-v] [-d crashdir] [-n dumpnr] [kernel [core]]\n", + getprogname()); + exit(1); +} + +static void +use_dump(int nr) +{ + char path[PATH_MAX]; + FILE *info; + char *s; + struct stat st; + int l; + + snprintf(path, sizeof(path), "%s/vmcore.%d", crashdir, nr); + if (stat(path, &st) == -1) + err(1, path); + if (!S_ISREG(st.st_mode)) + errx(1, "%s: not a regular file", path); + + vmcore = strdup(path); + + /* + * See if there's a kernel image right here, use it. The kernel + * image is either called kernel. or is in a subdirectory + * kernel. and called kernel. + */ + snprintf(path, sizeof(path), "%s/kernel.%d", crashdir, nr); + if (stat(path, &st) == 0) { + if (S_ISREG(st.st_mode)) { + kernel = strdup(path); + return; + } + if (S_ISDIR(st.st_mode)) { + snprintf(path, sizeof(path), "%s/kernel.%d/kernel", + crashdir, nr); + if (stat(path, &st) == 0 && S_ISREG(st.st_mode)) { + kernel = strdup(path); + return; + } + } + } + + /* + * No kernel image here. Parse the dump header. The kernel object + * directory can be found there and we probably have the kernel + * image in it still. + */ + snprintf(path, sizeof(path), "%s/info.%d", crashdir, nr); + info = fopen(path, "r"); + if (info == NULL) { + warn(path); + return; + } + while (fgets(path, sizeof(path), info) != NULL) { + l = strlen(path); + if (l > 0 && path[l - 1] == '\n') + path[--l] = '\0'; + if (strncmp(path, " ", 4) == 0) { + s = strchr(path, ':'); + s = (s == NULL) ? path + 4 : s + 1; + l = snprintf(path, sizeof(path), "%s/kernel.debug", s); + if (stat(path, &st) == -1 || !S_ISREG(st.st_mode)) { + path[l - 6] = '\0'; + if (stat(path, &st) == -1 || + !S_ISREG(st.st_mode)) + break; + } + kernel = strdup(path); + break; + } + } + fclose(info); + + if (verbose && kernel == NULL) + warnx("dump %d: no kernel found", nr); +} + +static void +kgdb_new_objfile(struct objfile *objfile) +{ +#if 0 + printf("XXX: %s(%p)\n", __func__, objfile); + if (objfile != NULL) { + goto out; + } + +out: +#endif + if (kgdb_new_objfile_chain != NULL) + kgdb_new_objfile_chain(objfile); +} + +static void +kgdb_interp_command_loop(void *data) +{ + static int once = 0; + + if (!once) { + symbol_file_add_main (kernel, 0); + print_stack_frame(get_current_frame(), -1, 0); + once = 1; + } + command_loop(); +} + +static void +kgdb_init(char *argv0 __unused) +{ + static struct interp_procs procs = { + NULL, + NULL, + NULL, + NULL, + NULL, + kgdb_interp_command_loop + }; + struct interp *kgdb; + kgdb = interp_new("kgdb", NULL, cli_out_new(gdb_stdout), &procs); + interp_add(kgdb); + + set_prompt("(kgdb) "); + kgdb_target(); + kgdb_new_objfile_chain = target_new_objfile_hook; + target_new_objfile_hook = kgdb_new_objfile; +} + +int +main(int argc, char *argv[]) +{ + struct captured_main_args args; + char *s; + int ch; + + dumpnr = -1; + + strlcpy(crashdir, "/var/crash", sizeof(crashdir)); + s = getenv("KGDB_CRASH_DIR"); + if (s != NULL) + strlcpy(crashdir, s, sizeof(crashdir)); + + while ((ch = getopt(argc, argv, "d:n:v")) != -1) { + switch (ch) { + case 'd': + strlcpy(crashdir, optarg, sizeof(crashdir)); + break; + case 'n': + dumpnr = strtol(optarg, &s, 0); + if (dumpnr < 0 || *s != '\0') { + warnx("option %c: invalid kernel dump number", + optopt); + usage(); + /* NOTREACHED */ + } + break; + case 'v': + verbose++; + break; + case '?': + default: + usage(); + } + } + + if (verbose > 1) + warnx("using %s as the crash directory", crashdir); + + if (dumpnr >= 0) + use_dump(dumpnr); + + if (argc > optind) { + if (kernel != NULL) + free(kernel); + kernel = strdup(argv[optind++]); + } + while (argc > optind) { + if (vmcore != NULL) + errx(1, "multiple core files specified"); + vmcore = strdup(argv[optind++]); + } + + if (kernel == NULL) + errx(1, "kernel not specified"); + if (vmcore == NULL) + errx(1, "core file not specified"); + + if (verbose) { + warnx("kernel image: %s", kernel); + warnx("core file: %s", vmcore); + } + + s = malloc(_POSIX2_LINE_MAX); + kvm = kvm_openfiles(kernel, vmcore, NULL, O_RDONLY, s); + if (kvm == NULL) + errx(1, s); + free(s); + + kgdb_thr_init(); + + memset (&args, 0, sizeof args); + args.argc = 1; + args.argv = argv; + args.use_windows = 0; + args.interpreter_p = "kgdb"; + + init_ui_hook = kgdb_init; + + return (gdb_main(&args)); +} diff --git a/gnu/usr.bin/gdb/kgdb/trgt.c b/gnu/usr.bin/gdb/kgdb/trgt.c new file mode 100644 index 00000000000..5c889eb3f34 --- /dev/null +++ b/gnu/usr.bin/gdb/kgdb/trgt.c @@ -0,0 +1,112 @@ +/* + * Copyright (c) 2004 Marcel Moolenaar + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include +__FBSDID("$FreeBSD$"); + +#include +#include + +#include "kgdb.h" + +#include +#include +#include +#include + +static struct target_ops kgdb_trgt_ops; + +static char * +kgdb_trgt_extra_thread_info(struct thread_info *ti __unused) +{ + return (NULL); +} + +static void +kgdb_trgt_find_new_threads(void) +{ +} + +static char * +kgdb_trgt_pid_to_str(ptid_t ptid) +{ + static char buf[16]; + + snprintf(buf, sizeof(buf), "TID %d", ptid_get_pid(ptid)); + return (buf); +} + +static int +kgdb_trgt_thread_alive(ptid_t ptid) +{ + return (kgdb_thr_lookup(ptid_get_pid(ptid)) != NULL); +} + +static int +kgdb_trgt_xfer_memory(CORE_ADDR memaddr, char *myaddr, int len, int write, + struct mem_attrib *attrib __unused, struct target_ops *target __unused) +{ + if (len == 0) + return (0); + + if (!write) + return (kvm_read(kvm, memaddr, myaddr, len)); + else + return (kvm_write(kvm, memaddr, myaddr, len)); +} + +void +kgdb_target(void) +{ + struct kthr *kt; + struct thread_info *ti; + + kgdb_trgt_ops.to_magic = OPS_MAGIC; + kgdb_trgt_ops.to_shortname = "kernel"; + kgdb_trgt_ops.to_longname = "kernel core files."; + kgdb_trgt_ops.to_doc = "Kernel core files."; + kgdb_trgt_ops.to_stratum = thread_stratum; + kgdb_trgt_ops.to_has_memory = 1; + kgdb_trgt_ops.to_has_registers = 1; + kgdb_trgt_ops.to_has_stack = 1; + + kgdb_trgt_ops.to_extra_thread_info = kgdb_trgt_extra_thread_info; + kgdb_trgt_ops.to_fetch_registers = kgdb_trgt_fetch_registers; + kgdb_trgt_ops.to_find_new_threads = kgdb_trgt_find_new_threads; + kgdb_trgt_ops.to_pid_to_str = kgdb_trgt_pid_to_str; + kgdb_trgt_ops.to_store_registers = kgdb_trgt_store_registers; + kgdb_trgt_ops.to_thread_alive = kgdb_trgt_thread_alive; + kgdb_trgt_ops.to_xfer_memory = kgdb_trgt_xfer_memory; + add_target(&kgdb_trgt_ops); + push_target(&kgdb_trgt_ops); + + kt = kgdb_thr_first(); + while (kt != NULL) { + ti = add_thread(ptid_build(kt->tid, 0, 0)); + kt = kgdb_thr_next(kt); + } + inferior_ptid = ptid_build(curkthr->tid, 0, 0); +} diff --git a/gnu/usr.bin/gdb/kgdb/trgt_alpha.c b/gnu/usr.bin/gdb/kgdb/trgt_alpha.c new file mode 100644 index 00000000000..891b0eb63e6 --- /dev/null +++ b/gnu/usr.bin/gdb/kgdb/trgt_alpha.c @@ -0,0 +1,73 @@ +/* + * Copyright (c) 2004 Marcel Moolenaar + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include +__FBSDID("$FreeBSD$"); + +#include +#include +#include +#include +#include + +#include "kgdb.h" + +#include +#include +#include +#include +#include + +void +kgdb_trgt_fetch_registers(int regno __unused) +{ + struct kthr *kt; + struct pcb pcb; + + kt = kgdb_thr_lookup(ptid_get_pid(inferior_ptid)); + if (kt == NULL) + return; + if (kvm_read(kvm, kt->pcb, &pcb, sizeof(pcb)) != sizeof(pcb)) { + warnx("kvm_read: %s", kvm_geterr(kvm)); + memset(&pcb, 0, sizeof(pcb)); + } + + supply_register(9, (char *)&pcb.pcb_context[0]); + supply_register(10, (char *)&pcb.pcb_context[1]); + supply_register(11, (char *)&pcb.pcb_context[2]); + supply_register(12, (char *)&pcb.pcb_context[3]); + supply_register(13, (char *)&pcb.pcb_context[4]); + supply_register(14, (char *)&pcb.pcb_context[5]); + supply_register(15, (char *)&pcb.pcb_context[6]); + supply_register(30, (char *)&pcb.pcb_hw.apcb_ksp); + supply_register(64, (char *)&pcb.pcb_context[7]); +} + +void +kgdb_trgt_store_registers(int regno __unused) +{ + fprintf_unfiltered(gdb_stderr, "XXX: %s\n", __func__); +} diff --git a/gnu/usr.bin/gdb/kgdb/trgt_amd64.c b/gnu/usr.bin/gdb/kgdb/trgt_amd64.c new file mode 100644 index 00000000000..e193969ca5c --- /dev/null +++ b/gnu/usr.bin/gdb/kgdb/trgt_amd64.c @@ -0,0 +1,73 @@ +/* + * Copyright (c) 2004 Marcel Moolenaar + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include +__FBSDID("$FreeBSD$"); + +#include +#include +#include +#include +#include + +#include "kgdb.h" + +#include +#include +#include +#include +#include + +void +kgdb_trgt_fetch_registers(int regno __unused) +{ + struct kthr *kt; + struct pcb pcb; + + kt = kgdb_thr_lookup(ptid_get_pid(inferior_ptid)); + if (kt == NULL) + return; + if (kvm_read(kvm, kt->pcb, &pcb, sizeof(pcb)) != sizeof(pcb)) { + warnx("kvm_read: %s", kvm_geterr(kvm)); + memset(&pcb, 0, sizeof(pcb)); + } + + supply_register(1, (char *)&pcb.pcb_rbx); + supply_register(6, (char *)&pcb.pcb_rbp); + supply_register(7, (char *)&pcb.pcb_rsp); + supply_register(12, (char *)&pcb.pcb_r12); + supply_register(13, (char *)&pcb.pcb_r13); + supply_register(14, (char *)&pcb.pcb_r14); + supply_register(15, (char *)&pcb.pcb_r15); + supply_register(16, (char *)&pcb.pcb_rip); + supply_register(17, (char *)&pcb.pcb_rflags); +} + +void +kgdb_trgt_store_registers(int regno __unused) +{ + fprintf_unfiltered(gdb_stderr, "XXX: %s\n", __func__); +} diff --git a/gnu/usr.bin/gdb/kgdb/trgt_i386.c b/gnu/usr.bin/gdb/kgdb/trgt_i386.c new file mode 100644 index 00000000000..36c1ed06754 --- /dev/null +++ b/gnu/usr.bin/gdb/kgdb/trgt_i386.c @@ -0,0 +1,69 @@ +/* + * Copyright (c) 2004 Marcel Moolenaar + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include +__FBSDID("$FreeBSD$"); + +#include +#include +#include +#include +#include + +#include "kgdb.h" + +#include +#include +#include +#include +#include + +void +kgdb_trgt_fetch_registers(int regno __unused) +{ + struct kthr *kt; + struct pcb pcb; + + kt = kgdb_thr_lookup(ptid_get_pid(inferior_ptid)); + if (kt == NULL) + return; + if (kvm_read(kvm, kt->pcb, &pcb, sizeof(pcb)) != sizeof(pcb)) { + warnx("kvm_read: %s", kvm_geterr(kvm)); + memset(&pcb, 0, sizeof(pcb)); + } + supply_register(3, (char *)&pcb.pcb_ebx); + supply_register(4, (char *)&pcb.pcb_esp); + supply_register(5, (char *)&pcb.pcb_ebp); + supply_register(6, (char *)&pcb.pcb_esi); + supply_register(7, (char *)&pcb.pcb_edi); + supply_register(8, (char *)&pcb.pcb_eip); +} + +void +kgdb_trgt_store_registers(int regno __unused) +{ + fprintf_unfiltered(gdb_stderr, "XXX: %s\n", __func__); +} diff --git a/gnu/usr.bin/gdb/kgdb/trgt_ia64.c b/gnu/usr.bin/gdb/kgdb/trgt_ia64.c new file mode 100644 index 00000000000..15609afe340 --- /dev/null +++ b/gnu/usr.bin/gdb/kgdb/trgt_ia64.c @@ -0,0 +1,133 @@ +/* + * Copyright (c) 2004 Marcel Moolenaar + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include +__FBSDID("$FreeBSD$"); + +#include +#include +#include +#include +#include +#include + +#include "kgdb.h" + +#include +#include +#include +#include +#include + +void +kgdb_trgt_fetch_registers(int regno __unused) +{ + struct kthr *kt; + struct pcb pcb; + uint64_t r; + + kt = kgdb_thr_lookup(ptid_get_pid(inferior_ptid)); + if (kt == NULL) + return; + if (kvm_read(kvm, kt->pcb, &pcb, sizeof(pcb)) != sizeof(pcb)) { + warnx("kvm_read: %s", kvm_geterr(kvm)); + memset(&pcb, 0, sizeof(pcb)); + } + + /* Registers 0-127: general registers. */ + supply_register(1, (char *)&pcb.pcb_special.gp); + supply_register(4, (char *)&pcb.pcb_preserved.gr4); + supply_register(5, (char *)&pcb.pcb_preserved.gr5); + supply_register(6, (char *)&pcb.pcb_preserved.gr6); + supply_register(7, (char *)&pcb.pcb_preserved.gr7); + supply_register(12, (char *)&pcb.pcb_special.sp); + supply_register(13, (char *)&pcb.pcb_special.tp); + + /* Registers 128-255: floating-point registers. */ + supply_register(130, (char *)&pcb.pcb_preserved_fp.fr2); + supply_register(131, (char *)&pcb.pcb_preserved_fp.fr3); + supply_register(132, (char *)&pcb.pcb_preserved_fp.fr4); + supply_register(133, (char *)&pcb.pcb_preserved_fp.fr5); + supply_register(144, (char *)&pcb.pcb_preserved_fp.fr16); + supply_register(145, (char *)&pcb.pcb_preserved_fp.fr17); + supply_register(146, (char *)&pcb.pcb_preserved_fp.fr18); + supply_register(147, (char *)&pcb.pcb_preserved_fp.fr19); + supply_register(148, (char *)&pcb.pcb_preserved_fp.fr20); + supply_register(149, (char *)&pcb.pcb_preserved_fp.fr21); + supply_register(150, (char *)&pcb.pcb_preserved_fp.fr22); + supply_register(151, (char *)&pcb.pcb_preserved_fp.fr23); + supply_register(152, (char *)&pcb.pcb_preserved_fp.fr24); + supply_register(153, (char *)&pcb.pcb_preserved_fp.fr25); + supply_register(154, (char *)&pcb.pcb_preserved_fp.fr26); + supply_register(155, (char *)&pcb.pcb_preserved_fp.fr27); + supply_register(156, (char *)&pcb.pcb_preserved_fp.fr28); + supply_register(157, (char *)&pcb.pcb_preserved_fp.fr29); + supply_register(158, (char *)&pcb.pcb_preserved_fp.fr30); + supply_register(159, (char *)&pcb.pcb_preserved_fp.fr31); + + /* Registers 320-327: branch registers. */ + if (pcb.pcb_special.__spare == ~0UL) + supply_register(320, (char *)&pcb.pcb_special.rp); + supply_register(321, (char *)&pcb.pcb_preserved.br1); + supply_register(322, (char *)&pcb.pcb_preserved.br2); + supply_register(323, (char *)&pcb.pcb_preserved.br3); + supply_register(324, (char *)&pcb.pcb_preserved.br4); + supply_register(325, (char *)&pcb.pcb_preserved.br5); + + /* Registers 328-333: misc. other registers. */ + supply_register(330, (char *)&pcb.pcb_special.pr); + if (pcb.pcb_special.__spare == ~0UL) { + r = pcb.pcb_special.iip + ((pcb.pcb_special.psr >> 41) & 3); + supply_register(331, (char *)&r); + supply_register(333, (char *)&pcb.pcb_special.cfm); + } else { + supply_register(331, (char *)&pcb.pcb_special.rp); + supply_register(333, (char *)&pcb.pcb_special.pfs); + } + + /* Registers 334-461: application registers. */ + supply_register(350, (char *)&pcb.pcb_special.rsc); + r = pcb.pcb_special.bspstore; + if (pcb.pcb_special.__spare == ~0UL) + r += pcb.pcb_special.ndirty; + else + r = ia64_bsp_adjust(r, IA64_CFM_SOF(pcb.pcb_special.pfs) - + IA64_CFM_SOL(pcb.pcb_special.pfs)); + supply_register(351, (char *)&r); /* bsp */ + supply_register(352, (char *)&r); /* bspstore */ + supply_register(353, (char *)&pcb.pcb_special.rnat); + supply_register(370, (char *)&pcb.pcb_special.unat); + supply_register(374, (char *)&pcb.pcb_special.fpsr); + if (pcb.pcb_special.__spare == ~0UL) + supply_register(398, (char *)&pcb.pcb_special.pfs); + supply_register(399, (char *)&pcb.pcb_preserved.lc); +} + +void +kgdb_trgt_store_registers(int regno __unused) +{ + fprintf_unfiltered(gdb_stderr, "XXX: %s\n", __func__); +} diff --git a/gnu/usr.bin/gdb/kgdb/trgt_sparc64.c b/gnu/usr.bin/gdb/kgdb/trgt_sparc64.c new file mode 100644 index 00000000000..81f9a86940f --- /dev/null +++ b/gnu/usr.bin/gdb/kgdb/trgt_sparc64.c @@ -0,0 +1,81 @@ +/* + * Copyright (c) 2004 Marcel Moolenaar + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include +__FBSDID("$FreeBSD$"); + +#include +#include +#include +#include +#include +#include + +#include "kgdb.h" + +#include +#include +#include +#include +#include + +void +kgdb_trgt_fetch_registers(int regno __unused) +{ + struct kthr *kt; + struct pcb pcb; + uint64_t r; + + kt = kgdb_thr_lookup(ptid_get_pid(inferior_ptid)); + if (kt == NULL) + return; + if (kvm_read(kvm, kt->pcb, &pcb, sizeof(pcb)) != sizeof(pcb)) { + warnx("kvm_read: %s", kvm_geterr(kvm)); + memset(&pcb, 0, sizeof(pcb)); + } + + /* 0-7: global registers (g0-g7) */ + + /* 8-15: output registers (o0-o7) */ + r = pcb.pcb_sp - CCFSZ; + supply_register(14, (char *)&r); + + /* 16-23: local registers (l0-l7) */ + + /* 24-31: input registers (i0-i7) */ + supply_register(30, (char *)&pcb.pcb_sp); + + /* 32-63: single precision FP (f0-f31) */ + + /* 64-79: double precision FP (f32-f62) */ + supply_register(80, (char *)&pcb.pcb_pc); +} + +void +kgdb_trgt_store_registers(int regno __unused) +{ + fprintf_unfiltered(gdb_stderr, "XXX: %s\n", __func__); +}