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

Subversion Repositories or1k

[/] [or1k/] [trunk/] [insight/] [gdb/] [gdbserver/] [low-sun3.c] - Blame information for rev 1774

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

Line No. Rev Author Line
1 578 markom
/* Low level interface to ptrace, for the remote server for GDB.
2
   Copyright 1986, 1987, 1993, 1994, 1995, 1999, 2000, 2001
3
   Free Software Foundation, Inc.
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
9
   the Free Software Foundation; either version 2 of the License, or
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
18
   along with this program; if not, write to the Free Software
19
   Foundation, Inc., 59 Temple Place - Suite 330,
20
   Boston, MA 02111-1307, USA.  */
21
 
22
#include "server.h"
23
#include "<sys/wait.h>"
24
#include "frame.h"
25
#include "inferior.h"
26
 
27
#include <stdio.h>
28
#include <sys/param.h>
29
#include <sys/dir.h>
30
#include <sys/user.h>
31
#include <signal.h>
32
#include <sys/ioctl.h>
33
#include <sgtty.h>
34
#include <fcntl.h>
35
 
36
/***************Begin MY defs*********************/
37
static char my_registers[REGISTER_BYTES];
38
char *registers = my_registers;
39
/***************End MY defs*********************/
40
 
41
#include <sys/ptrace.h>
42
#include <machine/reg.h>
43
 
44
extern int sys_nerr;
45
extern char **sys_errlist;
46
extern int errno;
47
 
48
/* Start an inferior process and returns its pid.
49
   ALLARGS is a vector of program-name and args. */
50
 
51
int
52
create_inferior (char *program, char **allargs)
53
{
54
  int pid;
55
 
56
  pid = fork ();
57
  if (pid < 0)
58
    perror_with_name ("fork");
59
 
60
  if (pid == 0)
61
    {
62
      ptrace (PTRACE_TRACEME);
63
 
64
      execv (program, allargs);
65
 
66
      fprintf (stderr, "Cannot exec %s: %s.\n", program,
67
               errno < sys_nerr ? sys_errlist[errno] : "unknown error");
68
      fflush (stderr);
69
      _exit (0177);
70
    }
71
 
72
  return pid;
73
}
74
 
75
/* Kill the inferior process.  Make us have no inferior.  */
76
 
77
void
78
kill_inferior (void)
79
{
80
  if (inferior_pid == 0)
81
    return;
82
  ptrace (8, inferior_pid, 0, 0);
83
  wait (0);
84
/*************inferior_died ();****VK**************/
85
}
86
 
87
/* Return nonzero if the given thread is still alive.  */
88
int
89
mythread_alive (int pid)
90
{
91
  return 1;
92
}
93
 
94
/* Wait for process, returns status */
95
 
96
unsigned char
97
mywait (char *status)
98
{
99
  int pid;
100
  union wait w;
101
 
102
  pid = wait (&w);
103
  if (pid != inferior_pid)
104
    perror_with_name ("wait");
105
 
106
  if (WIFEXITED (w))
107
    {
108
      fprintf (stderr, "\nChild exited with retcode = %x \n", WEXITSTATUS (w));
109
      *status = 'W';
110
      return ((unsigned char) WEXITSTATUS (w));
111
    }
112
  else if (!WIFSTOPPED (w))
113
    {
114
      fprintf (stderr, "\nChild terminated with signal = %x \n", WTERMSIG (w));
115
      *status = 'X';
116
      return ((unsigned char) WTERMSIG (w));
117
    }
118
 
119
  fetch_inferior_registers (0);
120
 
121
  *status = 'T';
122
  return ((unsigned char) WSTOPSIG (w));
123
}
124
 
125
/* Resume execution of the inferior process.
126
   If STEP is nonzero, single-step it.
127
   If SIGNAL is nonzero, give it that signal.  */
128
 
129
void
130
myresume (int step, int signal)
131
{
132
  errno = 0;
133
  ptrace (step ? PTRACE_SINGLESTEP : PTRACE_CONT, inferior_pid, 1, signal);
134
  if (errno)
135
    perror_with_name ("ptrace");
136
}
137
 
138
/* Fetch one or more registers from the inferior.  REGNO == -1 to get
139
   them all.  We actually fetch more than requested, when convenient,
140
   marking them as valid so we won't fetch them again.  */
141
 
142
void
143
fetch_inferior_registers (int ignored)
144
{
145
  struct regs inferior_registers;
146
  struct fp_status inferior_fp_registers;
147
 
148
  ptrace (PTRACE_GETREGS, inferior_pid,
149
          (PTRACE_ARG3_TYPE) & inferior_registers);
150
#ifdef FP0_REGNUM
151
  ptrace (PTRACE_GETFPREGS, inferior_pid,
152
          (PTRACE_ARG3_TYPE) & inferior_fp_registers);
153
#endif
154
 
155
  memcpy (registers, &inferior_registers, 16 * 4);
156
#ifdef FP0_REGNUM
157
  memcpy (&registers[REGISTER_BYTE (FP0_REGNUM)], &inferior_fp_registers,
158
          sizeof inferior_fp_registers.fps_regs);
159
#endif
160
  *(int *) &registers[REGISTER_BYTE (PS_REGNUM)] = inferior_registers.r_ps;
161
  *(int *) &registers[REGISTER_BYTE (PC_REGNUM)] = inferior_registers.r_pc;
162
#ifdef FP0_REGNUM
163
  memcpy
164
    (&registers[REGISTER_BYTE (FPC_REGNUM)],
165
     &inferior_fp_registers.fps_control,
166
     sizeof inferior_fp_registers - sizeof inferior_fp_registers.fps_regs);
167
#endif
168
}
169
 
170
/* Store our register values back into the inferior.
171
   If REGNO is -1, do this for all registers.
172
   Otherwise, REGNO specifies which register (so we can save time).  */
173
 
174
void
175
store_inferior_registers (int ignored)
176
{
177
  struct regs inferior_registers;
178
  struct fp_status inferior_fp_registers;
179
 
180
  memcpy (&inferior_registers, registers, 16 * 4);
181
#ifdef FP0_REGNUM
182
  memcpy (&inferior_fp_registers,
183
          &registers[REGISTER_BYTE (FP0_REGNUM)],
184
          sizeof inferior_fp_registers.fps_regs);
185
#endif
186
  inferior_registers.r_ps = *(int *) &registers[REGISTER_BYTE (PS_REGNUM)];
187
  inferior_registers.r_pc = *(int *) &registers[REGISTER_BYTE (PC_REGNUM)];
188
 
189
#ifdef FP0_REGNUM
190
  memcpy (&inferior_fp_registers.fps_control,
191
          &registers[REGISTER_BYTE (FPC_REGNUM)],
192
          (sizeof inferior_fp_registers
193
           - sizeof inferior_fp_registers.fps_regs));
194
#endif
195
 
196
  ptrace (PTRACE_SETREGS, inferior_pid,
197
          (PTRACE_ARG3_TYPE) & inferior_registers);
198
#if FP0_REGNUM
199
  ptrace (PTRACE_SETFPREGS, inferior_pid,
200
          (PTRACE_ARG3_TYPE) & inferior_fp_registers);
201
#endif
202
}
203
 
204
/* NOTE! I tried using PTRACE_READDATA, etc., to read and write memory
205
   in the NEW_SUN_PTRACE case.
206
   It ought to be straightforward.  But it appears that writing did
207
   not write the data that I specified.  I cannot understand where
208
   it got the data that it actually did write.  */
209
 
210
/* Copy LEN bytes from inferior's memory starting at MEMADDR
211
   to debugger memory starting at MYADDR.  */
212
 
213
void
214
read_inferior_memory (CORE_ADDR memaddr, char *myaddr, int len)
215
{
216
  register int i;
217
  /* Round starting address down to longword boundary.  */
218
  register CORE_ADDR addr = memaddr & -sizeof (int);
219
  /* Round ending address up; get number of longwords that makes.  */
220
  register int count
221
  = (((memaddr + len) - addr) + sizeof (int) - 1) / sizeof (int);
222
  /* Allocate buffer of that many longwords.  */
223
  register int *buffer = (int *) alloca (count * sizeof (int));
224
 
225
  /* Read all the longwords */
226
  for (i = 0; i < count; i++, addr += sizeof (int))
227
    {
228
      buffer[i] = ptrace (1, inferior_pid, addr, 0);
229
    }
230
 
231
  /* Copy appropriate bytes out of the buffer.  */
232
  memcpy (myaddr, (char *) buffer + (memaddr & (sizeof (int) - 1)), len);
233
}
234
 
235
/* Copy LEN bytes of data from debugger memory at MYADDR
236
   to inferior's memory at MEMADDR.
237
   On failure (cannot write the inferior)
238
   returns the value of errno.  */
239
 
240
int
241
write_inferior_memory (CORE_ADDR memaddr, char *myaddr, int len)
242
{
243
  register int i;
244
  /* Round starting address down to longword boundary.  */
245
  register CORE_ADDR addr = memaddr & -sizeof (int);
246
  /* Round ending address up; get number of longwords that makes.  */
247
  register int count
248
  = (((memaddr + len) - addr) + sizeof (int) - 1) / sizeof (int);
249
  /* Allocate buffer of that many longwords.  */
250
  register int *buffer = (int *) alloca (count * sizeof (int));
251
  extern int errno;
252
 
253
  /* Fill start and end extra bytes of buffer with existing memory data.  */
254
 
255
  buffer[0] = ptrace (1, inferior_pid, addr, 0);
256
 
257
  if (count > 1)
258
    {
259
      buffer[count - 1]
260
        = ptrace (1, inferior_pid,
261
                  addr + (count - 1) * sizeof (int), 0);
262
    }
263
 
264
  /* Copy data to be written over corresponding part of buffer */
265
 
266
  memcpy ((char *) buffer + (memaddr & (sizeof (int) - 1)), myaddr, len);
267
 
268
  /* Write the entire buffer.  */
269
 
270
  for (i = 0; i < count; i++, addr += sizeof (int))
271
    {
272
      errno = 0;
273
      ptrace (4, inferior_pid, addr, buffer[i]);
274
      if (errno)
275
        return errno;
276
    }
277
 
278
  return 0;
279
}
280
 
281
void
282
initialize_low (void)
283
{
284
}

powered by: WebSVN 2.1.0

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