1 |
douglas |
2 |
/* Kernel core dump functions below target vector, for GDB on FreeBSD/sparc64. |
2 |
|
|
Copyright 1986, 1987, 1989, 1991, 1992, 1993, 1994, 1995 |
3 |
|
|
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, Boston, MA 02111-1307, USA. |
20 |
|
|
*/ |
21 |
|
|
|
22 |
|
|
__FBSDID("$FreeBSD: ports/devel/gdb6/files/kvm-fbsd-sparc64.h,v 1.2 2004/08/23 06:34:48 obrien Exp $"); |
23 |
|
|
|
24 |
|
|
#include "sparc-tdep.h" |
25 |
|
|
|
26 |
|
|
#define SPARC_INTREG_SIZE 8 |
27 |
|
|
|
28 |
|
|
static void |
29 |
|
|
fetch_kcore_registers (struct pcb *pcbp) |
30 |
|
|
{ |
31 |
|
|
static struct frame top; |
32 |
|
|
CORE_ADDR f_addr; |
33 |
|
|
int i; |
34 |
|
|
|
35 |
|
|
/* Get the register values out of the sys pcb and store them where |
36 |
|
|
`read_register' will find them. */ |
37 |
|
|
/* |
38 |
|
|
* XXX many registers aren't available. |
39 |
|
|
* XXX for the non-core case, the registers are stale - they are for |
40 |
|
|
* the last context switch to the debugger. |
41 |
|
|
* XXX do something with the floating-point registers? |
42 |
|
|
*/ |
43 |
|
|
regcache_raw_supply (current_regcache, SP_REGNUM, &pcbp->pcb_sp); |
44 |
|
|
regcache_raw_supply (current_regcache, PC_REGNUM, &pcbp->pcb_pc); |
45 |
|
|
f_addr = extract_unsigned_integer (&pcbp->pcb_sp, SPARC_INTREG_SIZE); |
46 |
|
|
/* Load the previous frame by hand (XXX) and supply it. */ |
47 |
|
|
read_memory (f_addr + SPOFF, (char *)&top, sizeof (top)); |
48 |
|
|
for (i = 0; i < 8; i++) |
49 |
|
|
regcache_raw_supply (current_regcache, i + SPARC_L0_REGNUM, &top.fr_local[i]); |
50 |
|
|
for (i = 0; i < 8; i++) |
51 |
|
|
regcache_raw_supply (current_regcache, i + SPARC_I0_REGNUM, &top.fr_in[i]); |
52 |
|
|
} |
53 |
|
|
|
54 |
|
|
#if __FreeBSD_version >= 500032 |
55 |
|
|
CORE_ADDR |
56 |
|
|
fbsd_kern_frame_saved_pc (struct frame_info *fi) |
57 |
|
|
{ |
58 |
|
|
struct minimal_symbol *sym; |
59 |
|
|
CORE_ADDR frame, pc_addr, pc; |
60 |
|
|
char *buf; |
61 |
|
|
|
62 |
|
|
buf = alloca (MAX_REGISTER_SIZE); //or use DEPRECATED_MAX_REGISTER_RAW_SIZE |
63 |
|
|
/* XXX: duplicates fi->extra_info->bottom. */ |
64 |
|
|
frame = (get_next_frame (fi) != NULL) ? get_frame_base (get_next_frame (fi)) : read_sp (); |
65 |
|
|
pc_addr = frame + offsetof (struct frame, fr_in[7]); |
66 |
|
|
|
67 |
|
|
#define READ_PC(pc, a, b) do { \ |
68 |
|
|
read_memory (a, b, SPARC_INTREG_SIZE); \ |
69 |
|
|
pc = extract_unsigned_integer (b, SPARC_INTREG_SIZE); \ |
70 |
|
|
} while (0) |
71 |
|
|
|
72 |
|
|
READ_PC (pc, pc_addr, buf); |
73 |
|
|
|
74 |
|
|
sym = lookup_minimal_symbol_by_pc (pc); |
75 |
|
|
if (sym != NULL) |
76 |
|
|
{ |
77 |
|
|
if (strncmp (DEPRECATED_SYMBOL_NAME (sym), "tl0_", 4) == 0 || |
78 |
|
|
strcmp (DEPRECATED_SYMBOL_NAME (sym), "btext") == 0 || |
79 |
|
|
strcmp (DEPRECATED_SYMBOL_NAME (sym), "mp_startup") == 0 || |
80 |
|
|
strcmp (DEPRECATED_SYMBOL_NAME (sym), "fork_trampoline") == 0) |
81 |
|
|
{ |
82 |
|
|
/* |
83 |
|
|
* Ugly kluge: user space addresses aren't separated from kernel |
84 |
|
|
* ones by range; if encountering a trap from user space, just |
85 |
|
|
* return a 0 to stop the trace. |
86 |
|
|
* Do the same for entry points of kernel processes to avoid |
87 |
|
|
* printing garbage. |
88 |
|
|
*/ |
89 |
|
|
pc = 0; |
90 |
|
|
} |
91 |
|
|
if (strncmp (DEPRECATED_SYMBOL_NAME (sym), "tl1_", 4) == 0) |
92 |
|
|
{ |
93 |
|
|
pc_addr = get_frame_base (fi) + sizeof (struct frame) + |
94 |
|
|
offsetof (struct trapframe, tf_tpc); |
95 |
|
|
READ_PC (pc, pc_addr, buf); |
96 |
|
|
} |
97 |
|
|
} |
98 |
|
|
return (pc); |
99 |
|
|
} |
100 |
|
|
#endif |