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

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [gnu-stable/] [gdb-7.2/] [sim/] [rx/] [syscalls.c] - Blame information for rev 859

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

Line No. Rev Author Line
1 330 jeremybenn
/* syscalls.c --- implement system calls for the RX simulator.
2
 
3
Copyright (C) 2005, 2007, 2008, 2009, 2010 Free Software Foundation, Inc.
4
Contributed by Red Hat, Inc.
5
 
6
This file is part of the GNU simulators.
7
 
8
This program is free software; you can redistribute it and/or modify
9
it under the terms of the GNU General Public License as published by
10
the Free Software Foundation; either version 3 of the License, or
11
(at your option) any later version.
12
 
13
This program is distributed in the hope that it will be useful,
14
but WITHOUT ANY WARRANTY; without even the implied warranty of
15
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16
GNU General Public License for more details.
17
 
18
You should have received a copy of the GNU General Public License
19
along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
20
 
21
 
22
#include <stdio.h>
23
#include <stdlib.h>
24
#include <fcntl.h>
25
#include <unistd.h>
26
#include <sys/time.h>
27
 
28
#include "gdb/callback.h"
29
 
30
#include "cpu.h"
31
#include "mem.h"
32
#include "syscalls.h"
33
 
34
#include "syscall.h"
35
 
36
/* The current syscall callbacks we're using.  */
37
static struct host_callback_struct *callbacks;
38
 
39
void
40
set_callbacks (struct host_callback_struct *cb)
41
{
42
  callbacks = cb;
43
}
44
 
45
 
46
/* Arguments 1..4 are in R1..R4, remainder on stack.
47
 
48
   Return value in R1..R4 as needed.
49
     structs bigger than 16 bytes: pointer pushed on stack last
50
 
51
   We only support arguments that fit in general registers.
52
 
53
   The system call number is in R5.  We expect ssycalls to look like
54
   this in libgloss:
55
 
56
   _exit:
57
        mov     #SYS_exit, r5
58
        int     #255
59
        rts
60
*/
61
 
62
int argp, stackp;
63
 
64
static int
65
arg ()
66
{
67
  int rv = 0;
68
  argp++;
69
 
70
  if (argp < 4)
71
    return get_reg (argp);
72
 
73
  rv = mem_get_si (get_reg (sp) + stackp);
74
  stackp += 4;
75
  return rv;
76
}
77
 
78
static void
79
read_target (char *buffer, int address, int count, int asciiz)
80
{
81
  char byte;
82
  while (count > 0)
83
    {
84
      byte = mem_get_qi (address++);
85
      *buffer++ = byte;
86
      if (asciiz && (byte == 0))
87
        return;
88
      count--;
89
    }
90
}
91
 
92
static void
93
write_target (char *buffer, int address, int count, int asciiz)
94
{
95
  char byte;
96
  while (count > 0)
97
    {
98
      byte = *buffer++;
99
      mem_put_qi (address++, byte);
100
      if (asciiz && (byte == 0))
101
        return;
102
      count--;
103
    }
104
}
105
 
106
#define PTRSZ (A16 ? 2 : 3)
107
 
108
static char *callnames[] = {
109
  "SYS_zero",
110
  "SYS_exit",
111
  "SYS_open",
112
  "SYS_close",
113
  "SYS_read",
114
  "SYS_write",
115
  "SYS_lseek",
116
  "SYS_unlink",
117
  "SYS_getpid",
118
  "SYS_kill",
119
  "SYS_fstat",
120
  "SYS_sbrk",
121
  "SYS_argvlen",
122
  "SYS_argv",
123
  "SYS_chdir",
124
  "SYS_stat",
125
  "SYS_chmod",
126
  "SYS_utime",
127
  "SYS_time",
128
  "SYS_gettimeofday",
129
  "SYS_times",
130
  "SYS_link"
131
};
132
 
133
int
134
rx_syscall (int id)
135
{
136
  static char buf[256];
137
  int rv;
138
 
139
  argp = 0;
140
  stackp = 4;
141
  if (trace)
142
    printf ("\033[31m/* SYSCALL(%d) = %s */\033[0m\n", id, id <= SYS_link ? callnames[id] : "unknown");
143
  switch (id)
144
    {
145
    case SYS_exit:
146
      {
147
        int ec = arg ();
148
        if (verbose)
149
          printf ("[exit %d]\n", ec);
150
        return RX_MAKE_EXITED (ec);
151
      }
152
      break;
153
 
154
    case SYS_open:
155
      {
156
        int path = arg ();
157
        /* The open function is defined as taking a variable number of arguments
158
           because the third parameter to it is optional:
159
             open (const char * filename, int flags, ...);
160
           Hence the oflags and cflags arguments will be on the stack and we need
161
           to skip the (empty) argument registers r3 and r4.  */
162
        argp = 4;
163
        int oflags = arg ();
164
        int cflags = arg ();
165
 
166
        read_target (buf, path, 256, 1);
167
        if (trace)
168
          printf ("open(\"%s\",0x%x,%#o) = ", buf, oflags, cflags);
169
 
170
        if (callbacks)
171
          /* The callback vector ignores CFLAGS.  */
172
          rv = callbacks->open (callbacks, buf, oflags);
173
        else
174
          {
175
            int h_oflags = 0;
176
 
177
            if (oflags & 0x0001)
178
              h_oflags |= O_WRONLY;
179
            if (oflags & 0x0002)
180
              h_oflags |= O_RDWR;
181
            if (oflags & 0x0200)
182
              h_oflags |= O_CREAT;
183
            if (oflags & 0x0008)
184
              h_oflags |= O_APPEND;
185
            if (oflags & 0x0400)
186
              h_oflags |= O_TRUNC;
187
            rv = open (buf, h_oflags, cflags);
188
          }
189
        if (trace)
190
          printf ("%d\n", rv);
191
        put_reg (1, rv);
192
      }
193
      break;
194
 
195
    case SYS_close:
196
      {
197
        int fd = arg ();
198
 
199
        if (callbacks)
200
          rv = callbacks->close (callbacks, fd);
201
        else if (fd > 2)
202
          rv = close (fd);
203
        else
204
          rv = 0;
205
        if (trace)
206
          printf ("close(%d) = %d\n", fd, rv);
207
        put_reg (1, rv);
208
      }
209
      break;
210
 
211
    case SYS_read:
212
      {
213
        int fd = arg ();
214
        int addr = arg ();
215
        int count = arg ();
216
 
217
        if (count > sizeof (buf))
218
          count = sizeof (buf);
219
        if (callbacks)
220
          rv = callbacks->read (callbacks, fd, buf, count);
221
        else
222
          rv = read (fd, buf, count);
223
        if (trace)
224
          printf ("read(%d,%d) = %d\n", fd, count, rv);
225
        if (rv > 0)
226
          write_target (buf, addr, rv, 0);
227
        put_reg (1, rv);
228
      }
229
      break;
230
 
231
    case SYS_write:
232
      {
233
        int fd = arg ();
234
        int addr = arg ();
235
        int count = arg ();
236
 
237
        if (count > sizeof (buf))
238
          count = sizeof (buf);
239
        if (trace)
240
          printf ("write(%d,0x%x,%d)\n", fd, addr, count);
241
        read_target (buf, addr, count, 0);
242
        if (trace)
243
          fflush (stdout);
244
        if (callbacks)
245
          rv = callbacks->write (callbacks, fd, buf, count);
246
        else
247
          rv = write (fd, buf, count);
248
        if (trace)
249
          printf ("write(%d,%d) = %d\n", fd, count, rv);
250
        put_reg (1, rv);
251
      }
252
      break;
253
 
254
    case SYS_getpid:
255
      put_reg (1, 42);
256
      break;
257
 
258
    case SYS_gettimeofday:
259
      {
260
        int tvaddr = arg ();
261
        struct timeval tv;
262
 
263
        rv = gettimeofday (&tv, 0);
264
        if (trace)
265
          printf ("gettimeofday: %ld sec %ld usec to 0x%x\n", tv.tv_sec,
266
                  tv.tv_usec, tvaddr);
267
        mem_put_si (tvaddr, tv.tv_sec);
268
        mem_put_si (tvaddr + 4, tv.tv_usec);
269
        put_reg (1, rv);
270
      }
271
      break;
272
 
273
    case SYS_kill:
274
      {
275
        int pid = arg ();
276
        int sig = arg ();
277
        if (pid == 42)
278
          {
279
            if (verbose)
280
              printf ("[signal %d]\n", sig);
281
            return RX_MAKE_STOPPED (sig);
282
          }
283
      }
284
      break;
285
 
286
    case 11:
287
      {
288
        int heaptop_arg = arg ();
289
        if (trace)
290
          printf ("sbrk: heap top set to %x\n", heaptop_arg);
291
        heaptop = heaptop_arg;
292
        if (heapbottom == 0)
293
          heapbottom = heaptop_arg;
294
      }
295
      break;
296
 
297
    case 255:
298
      {
299
        int addr = arg ();
300
        mem_put_si (addr, rx_cycles + mem_usage_cycles());
301
      }
302
      break;
303
 
304
    }
305
  return RX_MAKE_STEPPED ();
306
}

powered by: WebSVN 2.1.0

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