gdb: add target_ops::supports_displaced_step
[deliverable/binutils-gdb.git] / gdb / sparc64-sol2-tdep.c
CommitLineData
386c036b
MK
1/* Target-dependent code for Solaris UltraSPARC.
2
b811d2c2 3 Copyright (C) 2003-2020 Free Software Foundation, Inc.
386c036b
MK
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
a9762ec7 9 the Free Software Foundation; either version 3 of the License, or
386c036b
MK
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
a9762ec7 18 along with this program. If not, see <http://www.gnu.org/licenses/>. */
386c036b
MK
19
20#include "defs.h"
21#include "frame.h"
22#include "frame-unwind.h"
23#include "gdbarch.h"
24#include "symtab.h"
25#include "objfiles.h"
26#include "osabi.h"
27#include "trad-frame.h"
ff1eb2b5 28#include "regset.h"
386c036b 29
081bf9da 30#include "sol2-tdep.h"
386c036b 31#include "sparc64-tdep.h"
70b216c8 32#include "solib-svr4.h"
386c036b
MK
33
34/* From <sys/regset.h>. */
b4fd25c9 35const struct sparc_gregmap sparc64_sol2_gregmap =
386c036b
MK
36{
37 32 * 8, /* "tstate" */
38 33 * 8, /* %pc */
39 34 * 8, /* %npc */
40 35 * 8, /* %y */
41 -1, /* %wim */
42 -1, /* %tbr */
43 1 * 8, /* %g1 */
44 16 * 8, /* %l0 */
45 8 /* sizeof (%y) */
46};
db75c717 47
b4fd25c9 48const struct sparc_fpregmap sparc64_sol2_fpregmap =
db75c717
DM
49{
50 0 * 8, /* %f0 */
51 33 * 8, /* %fsr */
52};
ff1eb2b5
UW
53
54static void
55sparc64_sol2_supply_core_gregset (const struct regset *regset,
56 struct regcache *regcache,
57 int regnum, const void *gregs, size_t len)
58{
59 sparc64_supply_gregset (&sparc64_sol2_gregmap, regcache, regnum, gregs);
60}
61
62static void
63sparc64_sol2_collect_core_gregset (const struct regset *regset,
64 const struct regcache *regcache,
65 int regnum, void *gregs, size_t len)
66{
67 sparc64_collect_gregset (&sparc64_sol2_gregmap, regcache, regnum, gregs);
68}
69
70static void
71sparc64_sol2_supply_core_fpregset (const struct regset *regset,
72 struct regcache *regcache,
73 int regnum, const void *fpregs, size_t len)
74{
75 sparc64_supply_fpregset (&sparc64_sol2_fpregmap, regcache, regnum, fpregs);
76}
77
78static void
79sparc64_sol2_collect_core_fpregset (const struct regset *regset,
80 const struct regcache *regcache,
81 int regnum, void *fpregs, size_t len)
82{
83 sparc64_collect_fpregset (&sparc64_sol2_fpregmap, regcache, regnum, fpregs);
84}
85
86static const struct regset sparc64_sol2_gregset =
87 {
88 NULL,
89 sparc64_sol2_supply_core_gregset,
90 sparc64_sol2_collect_core_gregset
91 };
92
93static const struct regset sparc64_sol2_fpregset =
94 {
95 NULL,
96 sparc64_sol2_supply_core_fpregset,
97 sparc64_sol2_collect_core_fpregset
98 };
386c036b
MK
99\f
100
101static struct sparc_frame_cache *
236369e7 102sparc64_sol2_sigtramp_frame_cache (struct frame_info *this_frame,
386c036b
MK
103 void **this_cache)
104{
105 struct sparc_frame_cache *cache;
106 CORE_ADDR mcontext_addr, addr;
107 int regnum;
108
109 if (*this_cache)
19ba03f4 110 return (struct sparc_frame_cache *) *this_cache;
386c036b 111
236369e7 112 cache = sparc_frame_cache (this_frame, this_cache);
386c036b
MK
113 gdb_assert (cache == *this_cache);
114
236369e7 115 cache->saved_regs = trad_frame_alloc_saved_regs (this_frame);
386c036b
MK
116
117 /* The third argument is a pointer to an instance of `ucontext_t',
118 which has a member `uc_mcontext' that contains the saved
119 registers. */
369c397b
JB
120 regnum =
121 (cache->copied_regs_mask & 0x04) ? SPARC_I2_REGNUM : SPARC_O2_REGNUM;
236369e7 122 mcontext_addr = get_frame_register_unsigned (this_frame, regnum) + 64;
386c036b
MK
123
124 cache->saved_regs[SPARC64_CCR_REGNUM].addr = mcontext_addr + 0 * 8;
125 cache->saved_regs[SPARC64_PC_REGNUM].addr = mcontext_addr + 1 * 8;
126 cache->saved_regs[SPARC64_NPC_REGNUM].addr = mcontext_addr + 2 * 8;
127 cache->saved_regs[SPARC64_Y_REGNUM].addr = mcontext_addr + 3 * 8;
128 cache->saved_regs[SPARC64_ASI_REGNUM].addr = mcontext_addr + 19 * 8;
129 cache->saved_regs[SPARC64_FPRS_REGNUM].addr = mcontext_addr + 20 * 8;
130
131 /* Since %g0 is always zero, keep the identity encoding. */
132 for (regnum = SPARC_G1_REGNUM, addr = mcontext_addr + 4 * 8;
133 regnum <= SPARC_O7_REGNUM; regnum++, addr += 8)
134 cache->saved_regs[regnum].addr = addr;
135
236369e7 136 if (get_frame_memory_unsigned (this_frame, mcontext_addr + 21 * 8, 8))
386c036b
MK
137 {
138 /* The register windows haven't been flushed. */
139 for (regnum = SPARC_L0_REGNUM; regnum <= SPARC_I7_REGNUM; regnum++)
140 trad_frame_set_unknown (cache->saved_regs, regnum);
141 }
142 else
143 {
144 CORE_ADDR sp;
145
146 addr = cache->saved_regs[SPARC_SP_REGNUM].addr;
236369e7 147 sp = get_frame_memory_unsigned (this_frame, addr, 8);
386c036b
MK
148 for (regnum = SPARC_L0_REGNUM, addr = sp + BIAS;
149 regnum <= SPARC_I7_REGNUM; regnum++, addr += 8)
150 cache->saved_regs[regnum].addr = addr;
151 }
152
153 return cache;
154}
155
156static void
236369e7 157sparc64_sol2_sigtramp_frame_this_id (struct frame_info *this_frame,
386c036b
MK
158 void **this_cache,
159 struct frame_id *this_id)
160{
161 struct sparc_frame_cache *cache =
236369e7 162 sparc64_sol2_sigtramp_frame_cache (this_frame, this_cache);
386c036b
MK
163
164 (*this_id) = frame_id_build (cache->base, cache->pc);
165}
166
236369e7
JB
167static struct value *
168sparc64_sol2_sigtramp_frame_prev_register (struct frame_info *this_frame,
386c036b 169 void **this_cache,
236369e7 170 int regnum)
386c036b
MK
171{
172 struct sparc_frame_cache *cache =
236369e7 173 sparc64_sol2_sigtramp_frame_cache (this_frame, this_cache);
386c036b 174
236369e7 175 return trad_frame_get_prev_register (this_frame, cache->saved_regs, regnum);
386c036b
MK
176}
177
236369e7
JB
178static int
179sparc64_sol2_sigtramp_frame_sniffer (const struct frame_unwind *self,
180 struct frame_info *this_frame,
181 void **this_cache)
386c036b 182{
236369e7 183 CORE_ADDR pc = get_frame_pc (this_frame);
2c02bd72 184 const char *name;
386c036b
MK
185
186 find_pc_partial_function (pc, &name, NULL, NULL);
187 if (sparc_sol2_pc_in_sigtramp (pc, name))
236369e7 188 return 1;
386c036b 189
236369e7 190 return 0;
386c036b 191}
236369e7
JB
192static const struct frame_unwind sparc64_sol2_sigtramp_frame_unwind =
193{
194 SIGTRAMP_FRAME,
8fbca658 195 default_frame_unwind_stop_reason,
236369e7
JB
196 sparc64_sol2_sigtramp_frame_this_id,
197 sparc64_sol2_sigtramp_frame_prev_register,
198 NULL,
199 sparc64_sol2_sigtramp_frame_sniffer
200};
201
386c036b
MK
202\f
203
204void
205sparc64_sol2_init_abi (struct gdbarch_info info, struct gdbarch *gdbarch)
206{
207 struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
208
ff1eb2b5
UW
209 tdep->gregset = &sparc64_sol2_gregset;
210 tdep->sizeof_gregset = 304;
211
212 tdep->fpregset = &sparc64_sol2_fpregset;
213 tdep->sizeof_fpregset = 544;
214
236369e7 215 frame_unwind_append_unwinder (gdbarch, &sparc64_sol2_sigtramp_frame_unwind);
386c036b
MK
216
217 sparc64_init_abi (info, gdbarch);
218
203c3895
UW
219 /* The Sun compilers (Sun ONE Studio, Forte Developer, Sun WorkShop, SunPRO)
220 compiler puts out 0 instead of the address in N_SO stabs. Starting with
221 SunPRO 3.0, the compiler does this for N_FUN stabs too. */
222 set_gdbarch_sofun_address_maybe_missing (gdbarch, 1);
223
149ad273
UW
224 /* The Sun compilers also do "globalization"; see the comment in
225 sparc_sol2_static_transform_name for more information. */
226 set_gdbarch_static_transform_name
227 (gdbarch, sparc_sol2_static_transform_name);
228
386c036b 229 /* Solaris has SVR4-style shared libraries... */
386c036b 230 set_gdbarch_skip_trampoline_code (gdbarch, find_solib_trampoline_target);
081bf9da 231 set_gdbarch_skip_solib_resolver (gdbarch, sol2_skip_solib_resolver);
70b216c8
MK
232 set_solib_svr4_fetch_link_map_offsets
233 (gdbarch, svr4_lp64_fetch_link_map_offsets);
386c036b
MK
234
235 /* ...which means that we need some special handling when doing
236 prologue analysis. */
237 tdep->plt_entry_size = 16;
238
239 /* Solaris has kernel-assisted single-stepping support. */
240 set_gdbarch_software_single_step (gdbarch, NULL);
959b8724 241
28439f5e
PA
242 /* How to print LWP PTIDs from core files. */
243 set_gdbarch_core_pid_to_str (gdbarch, sol2_core_pid_to_str);
386c036b 244}
386c036b 245
6c265988 246void _initialize_sparc64_sol2_tdep ();
386c036b 247void
6c265988 248_initialize_sparc64_sol2_tdep ()
386c036b
MK
249{
250 gdbarch_register_osabi (bfd_arch_sparc, bfd_mach_sparc_v9,
251 GDB_OSABI_SOLARIS, sparc64_sol2_init_abi);
252}
This page took 1.698115 seconds and 4 git commands to generate.