Merge {i386,amd64}_linux_read_description
[deliverable/binutils-gdb.git] / gdb / mips64obsd-tdep.c
CommitLineData
abc08782
MK
1/* Target-dependent code for OpenBSD/mips64.
2
ecd75fc8 3 Copyright (C) 2004-2014 Free Software Foundation, Inc.
abc08782
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
abc08782
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/>. */
abc08782
MK
19
20#include "defs.h"
89fa5cc8 21#include "gdbtypes.h"
abc08782
MK
22#include "osabi.h"
23#include "regcache.h"
24#include "regset.h"
8e763687
MK
25#include "trad-frame.h"
26#include "tramp-frame.h"
abc08782 27
8e763687 28#include "gdb_assert.h"
0e9f083f 29#include <string.h>
abc08782 30
3cdd631f 31#include "obsd-tdep.h"
abc08782
MK
32#include "mips-tdep.h"
33#include "solib-svr4.h"
34
89fa5cc8
MK
35/* The MIPS64 Floating-Point Quad-Precision format is similar to
36 big-endian IA-64 Quad-Precision format. */
37#define floatformats_mips64_quad floatformats_ia64_quad
38
abc08782
MK
39#define MIPS64OBSD_NUM_REGS 73
40
41/* Core file support. */
42
43/* Supply register REGNUM from the buffer specified by GREGS and LEN
44 in the general-purpose register set REGSET to register cache
45 REGCACHE. If REGNUM is -1, do this for all registers in REGSET. */
46
47static void
48mips64obsd_supply_gregset (const struct regset *regset,
49 struct regcache *regcache, int regnum,
50 const void *gregs, size_t len)
51{
52 const char *regs = gregs;
53 int i;
54
55 for (i = 0; i < MIPS64OBSD_NUM_REGS; i++)
56 {
57 if (regnum == i || regnum == -1)
58 regcache_raw_supply (regcache, i, regs + i * 8);
59 }
60}
61
62/* OpenBSD/mips64 register set. */
63
3ca7dae4 64static const struct regset mips64obsd_gregset =
abc08782
MK
65{
66 NULL,
67 mips64obsd_supply_gregset
68};
69
70/* Return the appropriate register set for the core section identified
71 by SECT_NAME and SECT_SIZE. */
72
73static const struct regset *
74mips64obsd_regset_from_core_section (struct gdbarch *gdbarch,
75 const char *sect_name, size_t sect_size)
76{
77 if (strcmp (sect_name, ".reg") == 0 && sect_size >= MIPS64OBSD_NUM_REGS * 8)
78 return &mips64obsd_gregset;
79
80 return NULL;
81}
82\f
83
8e763687
MK
84/* Signal trampolines. */
85
86static void
87mips64obsd_sigframe_init (const struct tramp_frame *self,
b8a22b94 88 struct frame_info *this_frame,
8e763687
MK
89 struct trad_frame_cache *cache,
90 CORE_ADDR func)
91{
b8a22b94 92 struct gdbarch *gdbarch = get_frame_arch (this_frame);
8e763687
MK
93 CORE_ADDR sp, sigcontext_addr, addr;
94 int regnum;
95
96 /* We find the appropriate instance of `struct sigcontext' at a
97 fixed offset in the signal frame. */
b8a22b94
DJ
98 sp = get_frame_register_signed (this_frame,
99 MIPS_SP_REGNUM + gdbarch_num_regs (gdbarch));
8e763687
MK
100 sigcontext_addr = sp + 32;
101
102 /* PC. */
103 regnum = mips_regnum (gdbarch)->pc;
f57d151a 104 trad_frame_set_reg_addr (cache,
2eb4d78b 105 regnum + gdbarch_num_regs (gdbarch),
f57d151a 106 sigcontext_addr + 16);
8e763687
MK
107
108 /* GPRs. */
109 for (regnum = MIPS_AT_REGNUM, addr = sigcontext_addr + 32;
110 regnum <= MIPS_RA_REGNUM; regnum++, addr += 8)
f57d151a 111 trad_frame_set_reg_addr (cache,
2eb4d78b 112 regnum + gdbarch_num_regs (gdbarch),
f57d151a 113 addr);
8e763687
MK
114
115 /* HI and LO. */
116 regnum = mips_regnum (gdbarch)->lo;
f57d151a 117 trad_frame_set_reg_addr (cache,
2eb4d78b 118 regnum + gdbarch_num_regs (gdbarch),
f57d151a 119 sigcontext_addr + 280);
8e763687 120 regnum = mips_regnum (gdbarch)->hi;
f57d151a 121 trad_frame_set_reg_addr (cache,
2eb4d78b 122 regnum + gdbarch_num_regs (gdbarch),
f57d151a 123 sigcontext_addr + 288);
8e763687
MK
124
125 /* TODO: Handle the floating-point registers. */
126
127 trad_frame_set_id (cache, frame_id_build (sp, func));
128}
129
130static const struct tramp_frame mips64obsd_sigframe =
131{
132 SIGTRAMP_FRAME,
133 MIPS_INSN32_SIZE,
134 {
135 { 0x67a40020, -1 }, /* daddiu a0,sp,32 */
136 { 0x24020067, -1 }, /* li v0,103 */
137 { 0x0000000c, -1 }, /* syscall */
138 { 0x0000000d, -1 }, /* break */
139 { TRAMP_SENTINEL_INSN, -1 }
140 },
141 mips64obsd_sigframe_init
142};
143
144\f
abc08782
MK
145static void
146mips64obsd_init_abi (struct gdbarch_info info, struct gdbarch *gdbarch)
147{
8e763687
MK
148 /* OpenBSD/mips64 only supports the n64 ABI, but the braindamaged
149 way GDB works, forces us to pretend we can handle them all. */
150
abc08782
MK
151 set_gdbarch_regset_from_core_section
152 (gdbarch, mips64obsd_regset_from_core_section);
153
8e763687
MK
154 tramp_frame_prepend_unwinder (gdbarch, &mips64obsd_sigframe);
155
89fa5cc8
MK
156 set_gdbarch_long_double_bit (gdbarch, 128);
157 set_gdbarch_long_double_format (gdbarch, floatformats_mips64_quad);
158
3cdd631f
MK
159 obsd_init_abi(info, gdbarch);
160
8e763687 161 /* OpenBSD/mips64 has SVR4-style shared libraries. */
abc08782
MK
162 set_solib_svr4_fetch_link_map_offsets
163 (gdbarch, svr4_lp64_fetch_link_map_offsets);
164}
165
166\f
167/* Provide a prototype to silence -Wmissing-prototypes. */
168void _initialize_mips64obsd_tdep (void);
169
170void
171_initialize_mips64obsd_tdep (void)
172{
173 gdbarch_register_osabi (bfd_arch_mips, 0, GDB_OSABI_OPENBSD_ELF,
174 mips64obsd_init_abi);
175}
This page took 0.829208 seconds and 4 git commands to generate.