Fix library-list.dtd -> library-list-svr4.dtd
[deliverable/binutils-gdb.git] / gdb / gdbserver / linux-ppc-low.c
CommitLineData
0a30fbc4
DJ
1/* GNU/Linux/PowerPC specific low level interface, for the remote server for
2 GDB.
ecd75fc8 3 Copyright (C) 1995-2014 Free Software Foundation, Inc.
0a30fbc4
DJ
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
0a30fbc4
DJ
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/>. */
0a30fbc4
DJ
19
20#include "server.h"
58caa3dc 21#include "linux-low.h"
0a30fbc4 22
b6430ec3 23#include <elf.h>
0a30fbc4
DJ
24#include <asm/ptrace.h>
25
b6430ec3 26/* These are in <asm/cputable.h> in current kernels. */
677c5bb1 27#define PPC_FEATURE_HAS_VSX 0x00000080
b6430ec3
UW
28#define PPC_FEATURE_HAS_ALTIVEC 0x10000000
29#define PPC_FEATURE_HAS_SPE 0x00800000
f4d9bade 30#define PPC_FEATURE_CELL 0x00010000
f04c6d38 31#define PPC_FEATURE_HAS_DFP 0x00000400
b6430ec3
UW
32
33static unsigned long ppc_hwcap;
34
35
7284e1be
UW
36/* Defined in auto-generated file powerpc-32l.c. */
37void init_registers_powerpc_32l (void);
3aee8918
PA
38extern const struct target_desc *tdesc_powerpc_32l;
39
7284e1be
UW
40/* Defined in auto-generated file powerpc-altivec32l.c. */
41void init_registers_powerpc_altivec32l (void);
3aee8918
PA
42extern const struct target_desc *tdesc_powerpc_altivec32l;
43
f4d9bade
UW
44/* Defined in auto-generated file powerpc-cell32l.c. */
45void init_registers_powerpc_cell32l (void);
3aee8918
PA
46extern const struct target_desc *tdesc_powerpc_cell32l;
47
677c5bb1
LM
48/* Defined in auto-generated file powerpc-vsx32l.c. */
49void init_registers_powerpc_vsx32l (void);
3aee8918
PA
50extern const struct target_desc *tdesc_powerpc_vsx32l;
51
2c4ad781
TJB
52/* Defined in auto-generated file powerpc-isa205-32l.c. */
53void init_registers_powerpc_isa205_32l (void);
3aee8918
PA
54extern const struct target_desc *tdesc_powerpc_isa205_32l;
55
2c4ad781
TJB
56/* Defined in auto-generated file powerpc-isa205-altivec32l.c. */
57void init_registers_powerpc_isa205_altivec32l (void);
3aee8918
PA
58extern const struct target_desc *tdesc_powerpc_isa205_altivec32l;
59
2c4ad781
TJB
60/* Defined in auto-generated file powerpc-isa205-vsx32l.c. */
61void init_registers_powerpc_isa205_vsx32l (void);
3aee8918
PA
62extern const struct target_desc *tdesc_powerpc_isa205_vsx32l;
63
7284e1be
UW
64/* Defined in auto-generated file powerpc-e500l.c. */
65void init_registers_powerpc_e500l (void);
3aee8918
PA
66extern const struct target_desc *tdesc_powerpc_e500l;
67
7284e1be
UW
68/* Defined in auto-generated file powerpc-64l.c. */
69void init_registers_powerpc_64l (void);
3aee8918
PA
70extern const struct target_desc *tdesc_powerpc_64l;
71
7284e1be
UW
72/* Defined in auto-generated file powerpc-altivec64l.c. */
73void init_registers_powerpc_altivec64l (void);
3aee8918
PA
74extern const struct target_desc *tdesc_powerpc_altivec64l;
75
f4d9bade
UW
76/* Defined in auto-generated file powerpc-cell64l.c. */
77void init_registers_powerpc_cell64l (void);
3aee8918
PA
78extern const struct target_desc *tdesc_powerpc_cell64l;
79
677c5bb1
LM
80/* Defined in auto-generated file powerpc-vsx64l.c. */
81void init_registers_powerpc_vsx64l (void);
3aee8918
PA
82extern const struct target_desc *tdesc_powerpc_vsx64l;
83
2c4ad781
TJB
84/* Defined in auto-generated file powerpc-isa205-64l.c. */
85void init_registers_powerpc_isa205_64l (void);
3aee8918
PA
86extern const struct target_desc *tdesc_powerpc_isa205_64l;
87
2c4ad781
TJB
88/* Defined in auto-generated file powerpc-isa205-altivec64l.c. */
89void init_registers_powerpc_isa205_altivec64l (void);
3aee8918
PA
90extern const struct target_desc *tdesc_powerpc_isa205_altivec64l;
91
2c4ad781
TJB
92/* Defined in auto-generated file powerpc-isa205-vsx64l.c. */
93void init_registers_powerpc_isa205_vsx64l (void);
3aee8918 94extern const struct target_desc *tdesc_powerpc_isa205_vsx64l;
7284e1be
UW
95
96#define ppc_num_regs 73
97
98/* This sometimes isn't defined. */
99#ifndef PT_ORIG_R3
100#define PT_ORIG_R3 34
101#endif
102#ifndef PT_TRAP
103#define PT_TRAP 40
104#endif
0a30fbc4 105
5b0a002e
UW
106#ifdef __powerpc64__
107/* We use a constant for FPSCR instead of PT_FPSCR, because
108 many shipped PPC64 kernels had the wrong value in ptrace.h. */
109static int ppc_regmap[] =
110 {PT_R0 * 8, PT_R1 * 8, PT_R2 * 8, PT_R3 * 8,
111 PT_R4 * 8, PT_R5 * 8, PT_R6 * 8, PT_R7 * 8,
112 PT_R8 * 8, PT_R9 * 8, PT_R10 * 8, PT_R11 * 8,
113 PT_R12 * 8, PT_R13 * 8, PT_R14 * 8, PT_R15 * 8,
114 PT_R16 * 8, PT_R17 * 8, PT_R18 * 8, PT_R19 * 8,
115 PT_R20 * 8, PT_R21 * 8, PT_R22 * 8, PT_R23 * 8,
116 PT_R24 * 8, PT_R25 * 8, PT_R26 * 8, PT_R27 * 8,
117 PT_R28 * 8, PT_R29 * 8, PT_R30 * 8, PT_R31 * 8,
118 PT_FPR0*8, PT_FPR0*8 + 8, PT_FPR0*8+16, PT_FPR0*8+24,
119 PT_FPR0*8+32, PT_FPR0*8+40, PT_FPR0*8+48, PT_FPR0*8+56,
120 PT_FPR0*8+64, PT_FPR0*8+72, PT_FPR0*8+80, PT_FPR0*8+88,
121 PT_FPR0*8+96, PT_FPR0*8+104, PT_FPR0*8+112, PT_FPR0*8+120,
122 PT_FPR0*8+128, PT_FPR0*8+136, PT_FPR0*8+144, PT_FPR0*8+152,
123 PT_FPR0*8+160, PT_FPR0*8+168, PT_FPR0*8+176, PT_FPR0*8+184,
124 PT_FPR0*8+192, PT_FPR0*8+200, PT_FPR0*8+208, PT_FPR0*8+216,
125 PT_FPR0*8+224, PT_FPR0*8+232, PT_FPR0*8+240, PT_FPR0*8+248,
126 PT_NIP * 8, PT_MSR * 8, PT_CCR * 8, PT_LNK * 8,
7284e1be
UW
127 PT_CTR * 8, PT_XER * 8, PT_FPR0*8 + 256,
128 PT_ORIG_R3 * 8, PT_TRAP * 8 };
5b0a002e 129#else
0a30fbc4 130/* Currently, don't check/send MQ. */
2ec06d2e 131static int ppc_regmap[] =
0a30fbc4
DJ
132 {PT_R0 * 4, PT_R1 * 4, PT_R2 * 4, PT_R3 * 4,
133 PT_R4 * 4, PT_R5 * 4, PT_R6 * 4, PT_R7 * 4,
134 PT_R8 * 4, PT_R9 * 4, PT_R10 * 4, PT_R11 * 4,
135 PT_R12 * 4, PT_R13 * 4, PT_R14 * 4, PT_R15 * 4,
136 PT_R16 * 4, PT_R17 * 4, PT_R18 * 4, PT_R19 * 4,
137 PT_R20 * 4, PT_R21 * 4, PT_R22 * 4, PT_R23 * 4,
138 PT_R24 * 4, PT_R25 * 4, PT_R26 * 4, PT_R27 * 4,
139 PT_R28 * 4, PT_R29 * 4, PT_R30 * 4, PT_R31 * 4,
140 PT_FPR0*4, PT_FPR0*4 + 8, PT_FPR0*4+16, PT_FPR0*4+24,
141 PT_FPR0*4+32, PT_FPR0*4+40, PT_FPR0*4+48, PT_FPR0*4+56,
142 PT_FPR0*4+64, PT_FPR0*4+72, PT_FPR0*4+80, PT_FPR0*4+88,
143 PT_FPR0*4+96, PT_FPR0*4+104, PT_FPR0*4+112, PT_FPR0*4+120,
144 PT_FPR0*4+128, PT_FPR0*4+136, PT_FPR0*4+144, PT_FPR0*4+152,
145 PT_FPR0*4+160, PT_FPR0*4+168, PT_FPR0*4+176, PT_FPR0*4+184,
146 PT_FPR0*4+192, PT_FPR0*4+200, PT_FPR0*4+208, PT_FPR0*4+216,
147 PT_FPR0*4+224, PT_FPR0*4+232, PT_FPR0*4+240, PT_FPR0*4+248,
148 PT_NIP * 4, PT_MSR * 4, PT_CCR * 4, PT_LNK * 4,
7284e1be
UW
149 PT_CTR * 4, PT_XER * 4, PT_FPSCR * 4,
150 PT_ORIG_R3 * 4, PT_TRAP * 4
b6430ec3
UW
151 };
152
153static int ppc_regmap_e500[] =
154 {PT_R0 * 4, PT_R1 * 4, PT_R2 * 4, PT_R3 * 4,
155 PT_R4 * 4, PT_R5 * 4, PT_R6 * 4, PT_R7 * 4,
156 PT_R8 * 4, PT_R9 * 4, PT_R10 * 4, PT_R11 * 4,
157 PT_R12 * 4, PT_R13 * 4, PT_R14 * 4, PT_R15 * 4,
158 PT_R16 * 4, PT_R17 * 4, PT_R18 * 4, PT_R19 * 4,
159 PT_R20 * 4, PT_R21 * 4, PT_R22 * 4, PT_R23 * 4,
160 PT_R24 * 4, PT_R25 * 4, PT_R26 * 4, PT_R27 * 4,
161 PT_R28 * 4, PT_R29 * 4, PT_R30 * 4, PT_R31 * 4,
162 -1, -1, -1, -1,
163 -1, -1, -1, -1,
164 -1, -1, -1, -1,
165 -1, -1, -1, -1,
166 -1, -1, -1, -1,
167 -1, -1, -1, -1,
168 -1, -1, -1, -1,
169 -1, -1, -1, -1,
170 PT_NIP * 4, PT_MSR * 4, PT_CCR * 4, PT_LNK * 4,
7284e1be
UW
171 PT_CTR * 4, PT_XER * 4, -1,
172 PT_ORIG_R3 * 4, PT_TRAP * 4
30ed0a8f 173 };
5b0a002e 174#endif
0a30fbc4 175
2ec06d2e
DJ
176static int
177ppc_cannot_store_register (int regno)
0a30fbc4 178{
3aee8918
PA
179 const struct target_desc *tdesc = current_process ()->tdesc;
180
b6430ec3 181#ifndef __powerpc64__
bc1e36ca 182 /* Some kernels do not allow us to store fpscr. */
3aee8918
PA
183 if (!(ppc_hwcap & PPC_FEATURE_HAS_SPE)
184 && regno == find_regno (tdesc, "fpscr"))
bc1e36ca 185 return 2;
30ed0a8f 186#endif
bc1e36ca 187
7284e1be 188 /* Some kernels do not allow us to store orig_r3 or trap. */
3aee8918
PA
189 if (regno == find_regno (tdesc, "orig_r3")
190 || regno == find_regno (tdesc, "trap"))
7284e1be
UW
191 return 2;
192
0a30fbc4
DJ
193 return 0;
194}
195
2ec06d2e
DJ
196static int
197ppc_cannot_fetch_register (int regno)
0a30fbc4
DJ
198{
199 return 0;
200}
201
5b0a002e 202static void
442ea881 203ppc_collect_ptrace_register (struct regcache *regcache, int regno, char *buf)
5b0a002e 204{
76b233dd
UW
205 memset (buf, 0, sizeof (long));
206
2e4bb98a
EBM
207 if (__BYTE_ORDER == __LITTLE_ENDIAN)
208 {
209 /* Little-endian values always sit at the left end of the buffer. */
210 collect_register (regcache, regno, buf);
211 }
212 else if (__BYTE_ORDER == __BIG_ENDIAN)
213 {
214 /* Big-endian values sit at the right end of the buffer. In case of
215 registers whose sizes are smaller than sizeof (long), we must use a
216 padding to access them correctly. */
217 int size = register_size (regcache->tdesc, regno);
218
219 if (size < sizeof (long))
220 collect_register (regcache, regno, buf + sizeof (long) - size);
221 else
222 collect_register (regcache, regno, buf);
223 }
5b0a002e 224 else
2e4bb98a 225 perror_with_name ("Unexpected byte order");
5b0a002e
UW
226}
227
228static void
442ea881
PA
229ppc_supply_ptrace_register (struct regcache *regcache,
230 int regno, const char *buf)
5b0a002e 231{
2e4bb98a
EBM
232 if (__BYTE_ORDER == __LITTLE_ENDIAN)
233 {
234 /* Little-endian values always sit at the left end of the buffer. */
235 supply_register (regcache, regno, buf);
236 }
237 else if (__BYTE_ORDER == __BIG_ENDIAN)
238 {
239 /* Big-endian values sit at the right end of the buffer. In case of
240 registers whose sizes are smaller than sizeof (long), we must use a
241 padding to access them correctly. */
242 int size = register_size (regcache->tdesc, regno);
243
244 if (size < sizeof (long))
245 supply_register (regcache, regno, buf + sizeof (long) - size);
246 else
247 supply_register (regcache, regno, buf);
248 }
5b0a002e 249 else
2e4bb98a 250 perror_with_name ("Unexpected byte order");
5b0a002e
UW
251}
252
0b9ff2c0
UW
253
254#define INSTR_SC 0x44000002
255#define NR_spu_run 0x0116
256
257/* If the PPU thread is currently stopped on a spu_run system call,
258 return to FD and ADDR the file handle and NPC parameter address
259 used with the system call. Return non-zero if successful. */
260static int
442ea881 261parse_spufs_run (struct regcache *regcache, int *fd, CORE_ADDR *addr)
0b9ff2c0
UW
262{
263 CORE_ADDR curr_pc;
264 int curr_insn;
265 int curr_r0;
266
3aee8918 267 if (register_size (regcache->tdesc, 0) == 4)
0b9ff2c0
UW
268 {
269 unsigned int pc, r0, r3, r4;
442ea881
PA
270 collect_register_by_name (regcache, "pc", &pc);
271 collect_register_by_name (regcache, "r0", &r0);
272 collect_register_by_name (regcache, "orig_r3", &r3);
273 collect_register_by_name (regcache, "r4", &r4);
0b9ff2c0
UW
274 curr_pc = (CORE_ADDR) pc;
275 curr_r0 = (int) r0;
276 *fd = (int) r3;
277 *addr = (CORE_ADDR) r4;
278 }
279 else
280 {
281 unsigned long pc, r0, r3, r4;
442ea881
PA
282 collect_register_by_name (regcache, "pc", &pc);
283 collect_register_by_name (regcache, "r0", &r0);
284 collect_register_by_name (regcache, "orig_r3", &r3);
285 collect_register_by_name (regcache, "r4", &r4);
0b9ff2c0
UW
286 curr_pc = (CORE_ADDR) pc;
287 curr_r0 = (int) r0;
288 *fd = (int) r3;
289 *addr = (CORE_ADDR) r4;
290 }
291
292 /* Fetch instruction preceding current NIP. */
293 if ((*the_target->read_memory) (curr_pc - 4,
294 (unsigned char *) &curr_insn, 4) != 0)
295 return 0;
296 /* It should be a "sc" instruction. */
297 if (curr_insn != INSTR_SC)
298 return 0;
299 /* System call number should be NR_spu_run. */
300 if (curr_r0 != NR_spu_run)
301 return 0;
302
303 return 1;
304}
305
0d62e5e8 306static CORE_ADDR
442ea881 307ppc_get_pc (struct regcache *regcache)
0d62e5e8 308{
0b9ff2c0
UW
309 CORE_ADDR addr;
310 int fd;
311
442ea881 312 if (parse_spufs_run (regcache, &fd, &addr))
0b9ff2c0
UW
313 {
314 unsigned int pc;
315 (*the_target->read_memory) (addr, (unsigned char *) &pc, 4);
493e2a69
MS
316 return ((CORE_ADDR)1 << 63)
317 | ((CORE_ADDR)fd << 32) | (CORE_ADDR) (pc - 4);
0b9ff2c0 318 }
3aee8918 319 else if (register_size (regcache->tdesc, 0) == 4)
6fe305f7
UW
320 {
321 unsigned int pc;
442ea881 322 collect_register_by_name (regcache, "pc", &pc);
6fe305f7
UW
323 return (CORE_ADDR) pc;
324 }
325 else
326 {
327 unsigned long pc;
442ea881 328 collect_register_by_name (regcache, "pc", &pc);
6fe305f7
UW
329 return (CORE_ADDR) pc;
330 }
0d62e5e8
DJ
331}
332
333static void
442ea881 334ppc_set_pc (struct regcache *regcache, CORE_ADDR pc)
0d62e5e8 335{
0b9ff2c0
UW
336 CORE_ADDR addr;
337 int fd;
338
442ea881 339 if (parse_spufs_run (regcache, &fd, &addr))
0b9ff2c0
UW
340 {
341 unsigned int newpc = pc;
342 (*the_target->write_memory) (addr, (unsigned char *) &newpc, 4);
343 }
3aee8918 344 else if (register_size (regcache->tdesc, 0) == 4)
6fe305f7
UW
345 {
346 unsigned int newpc = pc;
442ea881 347 supply_register_by_name (regcache, "pc", &newpc);
6fe305f7
UW
348 }
349 else
350 {
351 unsigned long newpc = pc;
442ea881 352 supply_register_by_name (regcache, "pc", &newpc);
6fe305f7
UW
353 }
354}
355
b6430ec3
UW
356
357static int
358ppc_get_hwcap (unsigned long *valp)
359{
3aee8918
PA
360 const struct target_desc *tdesc = current_process ()->tdesc;
361 int wordsize = register_size (tdesc, 0);
b6430ec3
UW
362 unsigned char *data = alloca (2 * wordsize);
363 int offset = 0;
364
365 while ((*the_target->read_auxv) (offset, data, 2 * wordsize) == 2 * wordsize)
366 {
367 if (wordsize == 4)
368 {
369 unsigned int *data_p = (unsigned int *)data;
370 if (data_p[0] == AT_HWCAP)
371 {
372 *valp = data_p[1];
373 return 1;
374 }
375 }
376 else
377 {
378 unsigned long *data_p = (unsigned long *)data;
379 if (data_p[0] == AT_HWCAP)
380 {
381 *valp = data_p[1];
382 return 1;
383 }
384 }
385
386 offset += 2 * wordsize;
387 }
388
389 *valp = 0;
390 return 0;
391}
392
3aee8918
PA
393/* Forward declaration. */
394static struct usrregs_info ppc_usrregs_info;
395#ifndef __powerpc64__
396static int ppc_regmap_adjusted;
397#endif
398
6fe305f7
UW
399static void
400ppc_arch_setup (void)
401{
3aee8918 402 const struct target_desc *tdesc;
6fe305f7
UW
403#ifdef __powerpc64__
404 long msr;
3be029c7 405 struct regcache *regcache;
0d62e5e8 406
c9b2f845
UW
407 /* On a 64-bit host, assume 64-bit inferior process with no
408 AltiVec registers. Reset ppc_hwcap to ensure that the
409 collect_register call below does not fail. */
3aee8918
PA
410 tdesc = tdesc_powerpc_64l;
411 current_process ()->tdesc = tdesc;
c9b2f845 412 ppc_hwcap = 0;
6fe305f7
UW
413
414 /* Only if the high bit of the MSR is set, we actually have
415 a 64-bit inferior. */
3aee8918
PA
416 regcache = new_register_cache (tdesc);
417 fetch_inferior_registers (regcache, find_regno (tdesc, "msr"));
3be029c7 418 collect_register_by_name (regcache, "msr", &msr);
92b72907 419 free_register_cache (regcache);
6fe305f7 420 if (msr < 0)
b6430ec3
UW
421 {
422 ppc_get_hwcap (&ppc_hwcap);
f4d9bade 423 if (ppc_hwcap & PPC_FEATURE_CELL)
3aee8918 424 tdesc = tdesc_powerpc_cell64l;
f4d9bade 425 else if (ppc_hwcap & PPC_FEATURE_HAS_VSX)
2c4ad781 426 {
f04c6d38
TJB
427 /* Power ISA 2.05 (implemented by Power 6 and newer processors)
428 increases the FPSCR from 32 bits to 64 bits. Even though Power 7
429 supports this ISA version, it doesn't have PPC_FEATURE_ARCH_2_05
430 set, only PPC_FEATURE_ARCH_2_06. Since for now the only bits
431 used in the higher half of the register are for Decimal Floating
432 Point, we check if that feature is available to decide the size
433 of the FPSCR. */
434 if (ppc_hwcap & PPC_FEATURE_HAS_DFP)
3aee8918 435 tdesc = tdesc_powerpc_isa205_vsx64l;
2c4ad781 436 else
3aee8918 437 tdesc = tdesc_powerpc_vsx64l;
2c4ad781 438 }
677c5bb1 439 else if (ppc_hwcap & PPC_FEATURE_HAS_ALTIVEC)
2c4ad781 440 {
f04c6d38 441 if (ppc_hwcap & PPC_FEATURE_HAS_DFP)
3aee8918 442 tdesc = tdesc_powerpc_isa205_altivec64l;
2c4ad781 443 else
3aee8918 444 tdesc = tdesc_powerpc_altivec64l;
2c4ad781
TJB
445 }
446
3aee8918 447 current_process ()->tdesc = tdesc;
b6430ec3
UW
448 return;
449 }
6fe305f7
UW
450#endif
451
452 /* OK, we have a 32-bit inferior. */
3aee8918
PA
453 tdesc = tdesc_powerpc_32l;
454 current_process ()->tdesc = tdesc;
b6430ec3
UW
455
456 ppc_get_hwcap (&ppc_hwcap);
f4d9bade 457 if (ppc_hwcap & PPC_FEATURE_CELL)
3aee8918 458 tdesc = tdesc_powerpc_cell32l;
f4d9bade 459 else if (ppc_hwcap & PPC_FEATURE_HAS_VSX)
2c4ad781 460 {
f04c6d38 461 if (ppc_hwcap & PPC_FEATURE_HAS_DFP)
3aee8918 462 tdesc = tdesc_powerpc_isa205_vsx32l;
2c4ad781 463 else
3aee8918 464 tdesc = tdesc_powerpc_vsx32l;
2c4ad781 465 }
677c5bb1 466 else if (ppc_hwcap & PPC_FEATURE_HAS_ALTIVEC)
2c4ad781 467 {
f04c6d38 468 if (ppc_hwcap & PPC_FEATURE_HAS_DFP)
3aee8918 469 tdesc = tdesc_powerpc_isa205_altivec32l;
2c4ad781 470 else
3aee8918 471 tdesc = tdesc_powerpc_altivec32l;
2c4ad781 472 }
677c5bb1 473
b6430ec3
UW
474 /* On 32-bit machines, check for SPE registers.
475 Set the low target's regmap field as appropriately. */
476#ifndef __powerpc64__
b6430ec3 477 if (ppc_hwcap & PPC_FEATURE_HAS_SPE)
3aee8918
PA
478 tdesc = tdesc_powerpc_e500l;
479
480 if (!ppc_regmap_adjusted)
b6430ec3 481 {
3aee8918
PA
482 if (ppc_hwcap & PPC_FEATURE_HAS_SPE)
483 ppc_usrregs_info.regmap = ppc_regmap_e500;
2c4ad781 484
3aee8918
PA
485 /* If the FPSCR is 64-bit wide, we need to fetch the whole
486 64-bit slot and not just its second word. The PT_FPSCR
487 supplied in a 32-bit GDB compilation doesn't reflect
488 this. */
489 if (register_size (tdesc, 70) == 8)
490 ppc_regmap[70] = (48 + 2*32) * sizeof (long);
491
492 ppc_regmap_adjusted = 1;
493 }
6fe305f7 494#endif
3aee8918 495 current_process ()->tdesc = tdesc;
0d62e5e8
DJ
496}
497
5b0a002e 498/* Correct in either endianness.
0d62e5e8
DJ
499 This instruction is "twge r2, r2", which GDB uses as a software
500 breakpoint. */
5b0a002e 501static const unsigned int ppc_breakpoint = 0x7d821008;
0d62e5e8
DJ
502#define ppc_breakpoint_len 4
503
504static int
505ppc_breakpoint_at (CORE_ADDR where)
506{
5b0a002e 507 unsigned int insn;
0d62e5e8 508
0b9ff2c0
UW
509 if (where & ((CORE_ADDR)1 << 63))
510 {
511 char mem_annex[32];
512 sprintf (mem_annex, "%d/mem", (int)((where >> 32) & 0x7fffffff));
513 (*the_target->qxfer_spu) (mem_annex, (unsigned char *) &insn,
514 NULL, where & 0xffffffff, 4);
515 if (insn == 0x3fff)
516 return 1;
517 }
518 else
519 {
520 (*the_target->read_memory) (where, (unsigned char *) &insn, 4);
521 if (insn == ppc_breakpoint)
522 return 1;
523 /* If necessary, recognize more trap instructions here. GDB only uses
524 the one. */
525 }
526
0d62e5e8
DJ
527 return 0;
528}
529
e9d25b98
DJ
530/* Provide only a fill function for the general register set. ps_lgetregs
531 will use this for NPTL support. */
532
442ea881 533static void ppc_fill_gregset (struct regcache *regcache, void *buf)
e9d25b98
DJ
534{
535 int i;
536
537 for (i = 0; i < 32; i++)
442ea881 538 ppc_collect_ptrace_register (regcache, i, (char *) buf + ppc_regmap[i]);
e9d25b98
DJ
539
540 for (i = 64; i < 70; i++)
442ea881 541 ppc_collect_ptrace_register (regcache, i, (char *) buf + ppc_regmap[i]);
7284e1be
UW
542
543 for (i = 71; i < 73; i++)
442ea881 544 ppc_collect_ptrace_register (regcache, i, (char *) buf + ppc_regmap[i]);
e9d25b98
DJ
545}
546
677c5bb1
LM
547#ifndef PTRACE_GETVSXREGS
548#define PTRACE_GETVSXREGS 27
549#define PTRACE_SETVSXREGS 28
550#endif
551
552#define SIZEOF_VSXREGS 32*8
553
554static void
442ea881 555ppc_fill_vsxregset (struct regcache *regcache, void *buf)
677c5bb1
LM
556{
557 int i, base;
558 char *regset = buf;
559
560 if (!(ppc_hwcap & PPC_FEATURE_HAS_VSX))
561 return;
562
3aee8918 563 base = find_regno (regcache->tdesc, "vs0h");
677c5bb1 564 for (i = 0; i < 32; i++)
442ea881 565 collect_register (regcache, base + i, &regset[i * 8]);
677c5bb1
LM
566}
567
568static void
442ea881 569ppc_store_vsxregset (struct regcache *regcache, const void *buf)
677c5bb1
LM
570{
571 int i, base;
572 const char *regset = buf;
573
574 if (!(ppc_hwcap & PPC_FEATURE_HAS_VSX))
575 return;
576
3aee8918 577 base = find_regno (regcache->tdesc, "vs0h");
677c5bb1 578 for (i = 0; i < 32; i++)
442ea881 579 supply_register (regcache, base + i, &regset[i * 8]);
677c5bb1
LM
580}
581
30ed0a8f
DJ
582#ifndef PTRACE_GETVRREGS
583#define PTRACE_GETVRREGS 18
584#define PTRACE_SETVRREGS 19
585#endif
586
587#define SIZEOF_VRREGS 33*16+4
588
589static void
442ea881 590ppc_fill_vrregset (struct regcache *regcache, void *buf)
30ed0a8f
DJ
591{
592 int i, base;
593 char *regset = buf;
594
b6430ec3
UW
595 if (!(ppc_hwcap & PPC_FEATURE_HAS_ALTIVEC))
596 return;
597
3aee8918 598 base = find_regno (regcache->tdesc, "vr0");
30ed0a8f 599 for (i = 0; i < 32; i++)
442ea881 600 collect_register (regcache, base + i, &regset[i * 16]);
30ed0a8f 601
442ea881
PA
602 collect_register_by_name (regcache, "vscr", &regset[32 * 16 + 12]);
603 collect_register_by_name (regcache, "vrsave", &regset[33 * 16]);
30ed0a8f
DJ
604}
605
606static void
442ea881 607ppc_store_vrregset (struct regcache *regcache, const void *buf)
30ed0a8f
DJ
608{
609 int i, base;
610 const char *regset = buf;
611
b6430ec3
UW
612 if (!(ppc_hwcap & PPC_FEATURE_HAS_ALTIVEC))
613 return;
614
3aee8918 615 base = find_regno (regcache->tdesc, "vr0");
30ed0a8f 616 for (i = 0; i < 32; i++)
442ea881 617 supply_register (regcache, base + i, &regset[i * 16]);
30ed0a8f 618
442ea881
PA
619 supply_register_by_name (regcache, "vscr", &regset[32 * 16 + 12]);
620 supply_register_by_name (regcache, "vrsave", &regset[33 * 16]);
30ed0a8f
DJ
621}
622
30ed0a8f
DJ
623#ifndef PTRACE_GETEVRREGS
624#define PTRACE_GETEVRREGS 20
625#define PTRACE_SETEVRREGS 21
626#endif
627
628struct gdb_evrregset_t
629{
630 unsigned long evr[32];
631 unsigned long long acc;
632 unsigned long spefscr;
633};
634
635static void
442ea881 636ppc_fill_evrregset (struct regcache *regcache, void *buf)
30ed0a8f
DJ
637{
638 int i, ev0;
639 struct gdb_evrregset_t *regset = buf;
640
b6430ec3
UW
641 if (!(ppc_hwcap & PPC_FEATURE_HAS_SPE))
642 return;
643
3aee8918 644 ev0 = find_regno (regcache->tdesc, "ev0h");
30ed0a8f 645 for (i = 0; i < 32; i++)
442ea881 646 collect_register (regcache, ev0 + i, &regset->evr[i]);
30ed0a8f 647
442ea881
PA
648 collect_register_by_name (regcache, "acc", &regset->acc);
649 collect_register_by_name (regcache, "spefscr", &regset->spefscr);
30ed0a8f
DJ
650}
651
652static void
442ea881 653ppc_store_evrregset (struct regcache *regcache, const void *buf)
30ed0a8f
DJ
654{
655 int i, ev0;
656 const struct gdb_evrregset_t *regset = buf;
657
b6430ec3
UW
658 if (!(ppc_hwcap & PPC_FEATURE_HAS_SPE))
659 return;
660
3aee8918 661 ev0 = find_regno (regcache->tdesc, "ev0h");
30ed0a8f 662 for (i = 0; i < 32; i++)
442ea881 663 supply_register (regcache, ev0 + i, &regset->evr[i]);
30ed0a8f 664
442ea881
PA
665 supply_register_by_name (regcache, "acc", &regset->acc);
666 supply_register_by_name (regcache, "spefscr", &regset->spefscr);
30ed0a8f 667}
30ed0a8f 668
3aee8918 669static struct regset_info ppc_regsets[] = {
30ed0a8f
DJ
670 /* List the extra register sets before GENERAL_REGS. That way we will
671 fetch them every time, but still fall back to PTRACE_PEEKUSER for the
672 general registers. Some kernels support these, but not the newer
673 PPC_PTRACE_GETREGS. */
1570b33e 674 { PTRACE_GETVSXREGS, PTRACE_SETVSXREGS, 0, SIZEOF_VSXREGS, EXTENDED_REGS,
677c5bb1 675 ppc_fill_vsxregset, ppc_store_vsxregset },
1570b33e 676 { PTRACE_GETVRREGS, PTRACE_SETVRREGS, 0, SIZEOF_VRREGS, EXTENDED_REGS,
30ed0a8f 677 ppc_fill_vrregset, ppc_store_vrregset },
1570b33e 678 { PTRACE_GETEVRREGS, PTRACE_SETEVRREGS, 0, 32 * 4 + 8 + 4, EXTENDED_REGS,
30ed0a8f 679 ppc_fill_evrregset, ppc_store_evrregset },
1570b33e
L
680 { 0, 0, 0, 0, GENERAL_REGS, ppc_fill_gregset, NULL },
681 { 0, 0, 0, -1, -1, NULL, NULL }
e9d25b98
DJ
682};
683
3aee8918
PA
684static struct usrregs_info ppc_usrregs_info =
685 {
686 ppc_num_regs,
687 ppc_regmap,
688 };
689
690static struct regsets_info ppc_regsets_info =
691 {
692 ppc_regsets, /* regsets */
693 0, /* num_regsets */
694 NULL, /* disabled_regsets */
695 };
696
697static struct regs_info regs_info =
698 {
699 NULL, /* regset_bitmap */
700 &ppc_usrregs_info,
701 &ppc_regsets_info
702 };
703
704static const struct regs_info *
705ppc_regs_info (void)
706{
707 return &regs_info;
708}
709
2ec06d2e 710struct linux_target_ops the_low_target = {
6fe305f7 711 ppc_arch_setup,
3aee8918 712 ppc_regs_info,
2ec06d2e
DJ
713 ppc_cannot_fetch_register,
714 ppc_cannot_store_register,
c14dfd32 715 NULL, /* fetch_register */
0d62e5e8
DJ
716 ppc_get_pc,
717 ppc_set_pc,
f450004a 718 (const unsigned char *) &ppc_breakpoint,
0d62e5e8
DJ
719 ppc_breakpoint_len,
720 NULL,
721 0,
722 ppc_breakpoint_at,
802e8e6d 723 NULL, /* supports_z_point_type */
5b0a002e
UW
724 NULL,
725 NULL,
726 NULL,
727 NULL,
728 ppc_collect_ptrace_register,
729 ppc_supply_ptrace_register,
2ec06d2e 730};
3aee8918
PA
731
732void
733initialize_low_arch (void)
734{
735 /* Initialize the Linux target descriptions. */
736
737 init_registers_powerpc_32l ();
738 init_registers_powerpc_altivec32l ();
739 init_registers_powerpc_cell32l ();
740 init_registers_powerpc_vsx32l ();
741 init_registers_powerpc_isa205_32l ();
742 init_registers_powerpc_isa205_altivec32l ();
743 init_registers_powerpc_isa205_vsx32l ();
744 init_registers_powerpc_e500l ();
745 init_registers_powerpc_64l ();
746 init_registers_powerpc_altivec64l ();
747 init_registers_powerpc_cell64l ();
748 init_registers_powerpc_vsx64l ();
749 init_registers_powerpc_isa205_64l ();
750 init_registers_powerpc_isa205_altivec64l ();
751 init_registers_powerpc_isa205_vsx64l ();
752
753 initialize_regsets_info (&ppc_regsets_info);
754}
This page took 1.030201 seconds and 4 git commands to generate.