OpenCores
URL https://opencores.org/ocsvn/openrisc_me/openrisc_me/trunk

Subversion Repositories openrisc_me

[/] [openrisc/] [trunk/] [gnu-src/] [gdb-6.8/] [gdb/] [gdbserver/] [linux-xtensa-low.c] - Blame information for rev 294

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 24 jeremybenn
/* GNU/Linux/Xtensa specific low level interface, for the remote server for GDB.
2
   Copyright 2007, 2008 Free Software Foundation, Inc.
3
 
4
   This file is part of GDB.
5
 
6
   This program is free software; you can redistribute it and/or modify
7
   it under the terms of the GNU General Public License as published by
8
   the Free Software Foundation; either version 3 of the License, or
9
   (at your option) any later version.
10
 
11
   This program is distributed in the hope that it will be useful,
12
   but WITHOUT ANY WARRANTY; without even the implied warranty of
13
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
   GNU General Public License for more details.
15
 
16
   You should have received a copy of the GNU General Public License
17
   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
18
 
19
 
20
#include "server.h"
21
#include "linux-low.h"
22
 
23
#include <sys/ptrace.h>
24
#include <xtensa-config.h>
25
 
26
#include "xtensa-xtregs.c"
27
 
28
enum regnum {
29
        R_PC=0,  R_PS,
30
        R_LBEG, R_LEND, R_LCOUNT,
31
        R_SAR,
32
        R_WS, R_WB,
33
        R_A0 = 64
34
};
35
 
36
static void
37
xtensa_fill_gregset (void *buf)
38
{
39
  elf_greg_t* rset = (elf_greg_t*)buf;
40
  int ar0_regnum;
41
  char *ptr;
42
  int i;
43
 
44
  /* Take care of AR registers.  */
45
 
46
  ar0_regnum = find_regno ("ar0");
47
  ptr = (char*)&rset[R_A0];
48
 
49
  for (i = ar0_regnum; i < ar0_regnum + XCHAL_NUM_AREGS; i++)
50
    {
51
      collect_register (i, ptr);
52
      ptr += register_size(i);
53
    }
54
 
55
  /* Loop registers, if hardware has it.  */
56
 
57
#if XCHAL_HAVE_LOOP
58
  collect_register_by_name ("lbeg", (char*)&rset[R_LBEG]);
59
  collect_register_by_name ("lend", (char*)&rset[R_LEND]);
60
  collect_register_by_name ("lcount", (char*)&rset[R_LCOUNT]);
61
#endif
62
 
63
  collect_register_by_name ("sar", (char*)&rset[R_SAR]);
64
  collect_register_by_name ("pc", (char*)&rset[R_PC]);
65
  collect_register_by_name ("ps", (char*)&rset[R_PS]);
66
  collect_register_by_name ("windowbase", (char*)&rset[R_WB]);
67
  collect_register_by_name ("windowstart", (char*)&rset[R_WS]);
68
}
69
 
70
static void
71
xtensa_store_gregset (const void *buf)
72
{
73
  const elf_greg_t* rset = (const elf_greg_t*)buf;
74
  int ar0_regnum;
75
  char *ptr;
76
  int i;
77
 
78
  /* Take care of AR registers.  */
79
 
80
  ar0_regnum = find_regno ("ar0");
81
  ptr = (char *)&rset[R_A0];
82
 
83
  for (i = ar0_regnum; i < ar0_regnum + XCHAL_NUM_AREGS; i++)
84
    {
85
      supply_register (i, ptr);
86
      ptr += register_size(i);
87
    }
88
 
89
  /* Loop registers, if hardware has it.  */
90
 
91
#if XCHAL_HAVE_LOOP
92
  supply_register_by_name ("lbeg", (char*)&rset[R_LBEG]);
93
  supply_register_by_name ("lend", (char*)&rset[R_LEND]);
94
  supply_register_by_name ("lcount", (char*)&rset[R_LCOUNT]);
95
#endif
96
 
97
  supply_register_by_name ("sar", (char*)&rset[R_SAR]);
98
  supply_register_by_name ("pc", (char*)&rset[R_PC]);
99
  supply_register_by_name ("ps", (char*)&rset[R_PS]);
100
  supply_register_by_name ("windowbase", (char*)&rset[R_WB]);
101
  supply_register_by_name ("windowstart", (char*)&rset[R_WS]);
102
}
103
 
104
/* Xtensa GNU/Linux PTRACE interface includes extended register set.  */
105
 
106
static void
107
xtensa_fill_xtregset (void *buf)
108
{
109
  const xtensa_regtable_t *ptr;
110
 
111
  for (ptr = xtensa_regmap_table; ptr->name; ptr++)
112
    {
113
      collect_register_by_name (ptr->name,
114
                                (char*)buf + ptr->ptrace_offset);
115
    }
116
}
117
 
118
static void
119
xtensa_store_xtregset (const void *buf)
120
{
121
  const xtensa_regtable_t *ptr;
122
 
123
  for (ptr = xtensa_regmap_table; ptr->name; ptr++)
124
    {
125
      supply_register_by_name (ptr->name,
126
                                (char*)buf + ptr->ptrace_offset);
127
    }
128
}
129
 
130
struct regset_info target_regsets[] = {
131
  { PTRACE_GETREGS, PTRACE_SETREGS, sizeof (elf_gregset_t),
132
    GENERAL_REGS,
133
    xtensa_fill_gregset, xtensa_store_gregset },
134
  { PTRACE_GETXTREGS, PTRACE_SETXTREGS, XTENSA_ELF_XTREG_SIZE,
135
    EXTENDED_REGS,
136
    xtensa_fill_xtregset, xtensa_store_xtregset },
137
  { 0, 0, -1, -1, NULL, NULL }
138
};
139
 
140
#if XCHAL_HAVE_BE
141
#define XTENSA_BREAKPOINT {0xd2,0x0f}
142
#else
143
#define XTENSA_BREAKPOINT {0x2d,0xf0}
144
#endif
145
 
146
static const unsigned char xtensa_breakpoint[] = XTENSA_BREAKPOINT;
147
#define xtensa_breakpoint_len 2
148
 
149
static CORE_ADDR
150
xtensa_get_pc (void)
151
{
152
  unsigned long pc;
153
 
154
  collect_register_by_name ("pc", &pc);
155
  return pc;
156
}
157
 
158
static void
159
xtensa_set_pc (CORE_ADDR pc)
160
{
161
  unsigned long newpc = pc;
162
  supply_register_by_name ("pc", &newpc);
163
}
164
 
165
static int
166
xtensa_breakpoint_at (CORE_ADDR where)
167
{
168
    unsigned long insn;
169
 
170
    (*the_target->read_memory) (where, (unsigned char *) &insn,
171
                                xtensa_breakpoint_len);
172
    return memcmp((char *)&insn, xtensa_breakpoint, xtensa_breakpoint_len) == 0;
173
}
174
 
175
struct linux_target_ops the_low_target = {
176
  0,
177
  0,
178
  0,
179
  0,
180
  xtensa_get_pc,
181
  xtensa_set_pc,
182
  xtensa_breakpoint,
183
  xtensa_breakpoint_len,
184
  NULL,
185
  0,
186
  xtensa_breakpoint_at,
187
};

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.