Add support for single register window model on SPARC
[deliverable/binutils-gdb.git] / gdb / sparc64-sol2-tdep.c
CommitLineData
386c036b
MK
1/* Target-dependent code for Solaris UltraSPARC.
2
7b6bb8da 3 Copyright (C) 2003, 2004, 2006, 2007, 2008, 2009, 2010, 2011
0fb0cc75 4 Free Software Foundation, Inc.
386c036b
MK
5
6 This file is part of GDB.
7
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
a9762ec7 10 the Free Software Foundation; either version 3 of the License, or
386c036b
MK
11 (at your option) any later version.
12
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
a9762ec7 19 along with this program. If not, see <http://www.gnu.org/licenses/>. */
386c036b
MK
20
21#include "defs.h"
22#include "frame.h"
23#include "frame-unwind.h"
24#include "gdbarch.h"
25#include "symtab.h"
26#include "objfiles.h"
27#include "osabi.h"
28#include "trad-frame.h"
29
30#include "gdb_assert.h"
31
081bf9da 32#include "sol2-tdep.h"
386c036b 33#include "sparc64-tdep.h"
70b216c8 34#include "solib-svr4.h"
386c036b
MK
35
36/* From <sys/regset.h>. */
37const struct sparc_gregset sparc64_sol2_gregset =
38{
39 32 * 8, /* "tstate" */
40 33 * 8, /* %pc */
41 34 * 8, /* %npc */
42 35 * 8, /* %y */
43 -1, /* %wim */
44 -1, /* %tbr */
45 1 * 8, /* %g1 */
46 16 * 8, /* %l0 */
47 8 /* sizeof (%y) */
48};
49\f
50
51static struct sparc_frame_cache *
236369e7 52sparc64_sol2_sigtramp_frame_cache (struct frame_info *this_frame,
386c036b
MK
53 void **this_cache)
54{
55 struct sparc_frame_cache *cache;
56 CORE_ADDR mcontext_addr, addr;
57 int regnum;
58
59 if (*this_cache)
60 return *this_cache;
61
236369e7 62 cache = sparc_frame_cache (this_frame, this_cache);
386c036b
MK
63 gdb_assert (cache == *this_cache);
64
236369e7 65 cache->saved_regs = trad_frame_alloc_saved_regs (this_frame);
386c036b
MK
66
67 /* The third argument is a pointer to an instance of `ucontext_t',
68 which has a member `uc_mcontext' that contains the saved
69 registers. */
369c397b
JB
70 regnum =
71 (cache->copied_regs_mask & 0x04) ? SPARC_I2_REGNUM : SPARC_O2_REGNUM;
236369e7 72 mcontext_addr = get_frame_register_unsigned (this_frame, regnum) + 64;
386c036b
MK
73
74 cache->saved_regs[SPARC64_CCR_REGNUM].addr = mcontext_addr + 0 * 8;
75 cache->saved_regs[SPARC64_PC_REGNUM].addr = mcontext_addr + 1 * 8;
76 cache->saved_regs[SPARC64_NPC_REGNUM].addr = mcontext_addr + 2 * 8;
77 cache->saved_regs[SPARC64_Y_REGNUM].addr = mcontext_addr + 3 * 8;
78 cache->saved_regs[SPARC64_ASI_REGNUM].addr = mcontext_addr + 19 * 8;
79 cache->saved_regs[SPARC64_FPRS_REGNUM].addr = mcontext_addr + 20 * 8;
80
81 /* Since %g0 is always zero, keep the identity encoding. */
82 for (regnum = SPARC_G1_REGNUM, addr = mcontext_addr + 4 * 8;
83 regnum <= SPARC_O7_REGNUM; regnum++, addr += 8)
84 cache->saved_regs[regnum].addr = addr;
85
236369e7 86 if (get_frame_memory_unsigned (this_frame, mcontext_addr + 21 * 8, 8))
386c036b
MK
87 {
88 /* The register windows haven't been flushed. */
89 for (regnum = SPARC_L0_REGNUM; regnum <= SPARC_I7_REGNUM; regnum++)
90 trad_frame_set_unknown (cache->saved_regs, regnum);
91 }
92 else
93 {
94 CORE_ADDR sp;
95
96 addr = cache->saved_regs[SPARC_SP_REGNUM].addr;
236369e7 97 sp = get_frame_memory_unsigned (this_frame, addr, 8);
386c036b
MK
98 for (regnum = SPARC_L0_REGNUM, addr = sp + BIAS;
99 regnum <= SPARC_I7_REGNUM; regnum++, addr += 8)
100 cache->saved_regs[regnum].addr = addr;
101 }
102
103 return cache;
104}
105
106static void
236369e7 107sparc64_sol2_sigtramp_frame_this_id (struct frame_info *this_frame,
386c036b
MK
108 void **this_cache,
109 struct frame_id *this_id)
110{
111 struct sparc_frame_cache *cache =
236369e7 112 sparc64_sol2_sigtramp_frame_cache (this_frame, this_cache);
386c036b
MK
113
114 (*this_id) = frame_id_build (cache->base, cache->pc);
115}
116
236369e7
JB
117static struct value *
118sparc64_sol2_sigtramp_frame_prev_register (struct frame_info *this_frame,
386c036b 119 void **this_cache,
236369e7 120 int regnum)
386c036b
MK
121{
122 struct sparc_frame_cache *cache =
236369e7 123 sparc64_sol2_sigtramp_frame_cache (this_frame, this_cache);
386c036b 124
236369e7 125 return trad_frame_get_prev_register (this_frame, cache->saved_regs, regnum);
386c036b
MK
126}
127
236369e7
JB
128static int
129sparc64_sol2_sigtramp_frame_sniffer (const struct frame_unwind *self,
130 struct frame_info *this_frame,
131 void **this_cache)
386c036b 132{
236369e7 133 CORE_ADDR pc = get_frame_pc (this_frame);
386c036b
MK
134 char *name;
135
136 find_pc_partial_function (pc, &name, NULL, NULL);
137 if (sparc_sol2_pc_in_sigtramp (pc, name))
236369e7 138 return 1;
386c036b 139
236369e7 140 return 0;
386c036b 141}
236369e7
JB
142static const struct frame_unwind sparc64_sol2_sigtramp_frame_unwind =
143{
144 SIGTRAMP_FRAME,
8fbca658 145 default_frame_unwind_stop_reason,
236369e7
JB
146 sparc64_sol2_sigtramp_frame_this_id,
147 sparc64_sol2_sigtramp_frame_prev_register,
148 NULL,
149 sparc64_sol2_sigtramp_frame_sniffer
150};
151
386c036b
MK
152\f
153
154void
155sparc64_sol2_init_abi (struct gdbarch_info info, struct gdbarch *gdbarch)
156{
157 struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
158
236369e7 159 frame_unwind_append_unwinder (gdbarch, &sparc64_sol2_sigtramp_frame_unwind);
386c036b
MK
160
161 sparc64_init_abi (info, gdbarch);
162
203c3895
UW
163 /* The Sun compilers (Sun ONE Studio, Forte Developer, Sun WorkShop, SunPRO)
164 compiler puts out 0 instead of the address in N_SO stabs. Starting with
165 SunPRO 3.0, the compiler does this for N_FUN stabs too. */
166 set_gdbarch_sofun_address_maybe_missing (gdbarch, 1);
167
149ad273
UW
168 /* The Sun compilers also do "globalization"; see the comment in
169 sparc_sol2_static_transform_name for more information. */
170 set_gdbarch_static_transform_name
171 (gdbarch, sparc_sol2_static_transform_name);
172
386c036b 173 /* Solaris has SVR4-style shared libraries... */
386c036b 174 set_gdbarch_skip_trampoline_code (gdbarch, find_solib_trampoline_target);
081bf9da 175 set_gdbarch_skip_solib_resolver (gdbarch, sol2_skip_solib_resolver);
70b216c8
MK
176 set_solib_svr4_fetch_link_map_offsets
177 (gdbarch, svr4_lp64_fetch_link_map_offsets);
386c036b
MK
178
179 /* ...which means that we need some special handling when doing
180 prologue analysis. */
181 tdep->plt_entry_size = 16;
182
183 /* Solaris has kernel-assisted single-stepping support. */
184 set_gdbarch_software_single_step (gdbarch, NULL);
959b8724 185
28439f5e
PA
186 /* How to print LWP PTIDs from core files. */
187 set_gdbarch_core_pid_to_str (gdbarch, sol2_core_pid_to_str);
386c036b
MK
188}
189\f
190
191/* Provide a prototype to silence -Wmissing-prototypes. */
192void _initialize_sparc64_sol2_tdep (void);
193
194void
195_initialize_sparc64_sol2_tdep (void)
196{
197 gdbarch_register_osabi (bfd_arch_sparc, bfd_mach_sparc_v9,
198 GDB_OSABI_SOLARIS, sparc64_sol2_init_abi);
199}
This page took 1.118848 seconds and 4 git commands to generate.