1 /* Remote target system call support.
2 Copyright 1997 Free Software Foundation, Inc.
3 Contributed by Cygnus Solutions.
5 This file is part of GDB.
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.
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.
17 You should have received a copy of the GNU General Public License
18 along with GAS; see the file COPYING. If not, write to the Free Software
19 Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
21 /* This interface isn't intended to be specific to any particular kind
22 of remote (hardware, simulator, whatever). As such, support for it
23 (e.g. sim/common/callback.c) should *not* live in the simulator source
24 tree, nor should it live in the gdb source tree. K&R C must be
31 #include "libiberty.h"
32 #ifdef ANSI_PROTOTYPES
47 #include <sys/types.h>
50 #include "targ-vals.h"
56 #define ENAMETOOLONG EINVAL
59 /* Maximum length of a path name. */
61 #define MAX_PATH_LEN 1024
64 /* When doing file read/writes, do this many bytes at a time. */
65 #define FILE_XFR_SIZE 4096
67 /* FIXME: for now, need to consider target word size. */
69 #define TADDR unsigned long
71 /* Utility of cb_syscall to fetch a path name or other string from the target.
72 The result is 0 for success or a host errno value. */
75 get_string (cb
, sc
, buf
, buflen
, addr
)
84 for (p
= buf
, pend
= buf
+ buflen
; p
< pend
; ++p
, ++addr
)
86 /* No, it isn't expected that this would cause one transaction with
87 the remote target for each byte. The target could send the
88 path name along with the syscall request, and cache the file
89 name somewhere (or otherwise tweak this as desired). */
90 unsigned int count
= (*sc
->read_mem
) (cb
, sc
, addr
, p
, 1);
102 /* Utility of cb_syscall to fetch a path name.
103 The buffer is malloc'd and the address is stored in BUFP.
104 The result is that of get_string.
105 If an error occurs, no buffer is left malloc'd. */
108 get_path (cb
, sc
, addr
, bufp
)
114 char *buf
= xmalloc (MAX_PATH_LEN
);
117 result
= get_string (cb
, sc
, buf
, MAX_PATH_LEN
, addr
);
125 /* Perform a system call on behalf of the target. */
126 /* FIXME: TODO: Add magic number to CB_SYSCALL, macro to initialize it,
127 and test for the magic number here. */
134 TWORD result
= 0, errcode
= 0;
136 if (sc
->magic
!= CB_SYSCALL_MAGIC
)
139 switch (cb_target_to_host_syscall (cb
, sc
->func
))
141 #if 0 /* FIXME: wip */
142 case CB_SYS_argvlen
:
144 /* Compute how much space is required to store the argv,envp
145 strings so that the program can allocate the space and then
146 call SYS_argv to fetch the values. */
147 int addr_size
= cb
->addr_size
;
148 int argc
,envc
,arglen
,envlen
;
149 const char **argv
= cb
->init_argv
;
150 const char **envp
= cb
->init_envp
;
155 for ( ; argv
[argc
]; ++argc
)
156 arglen
+= strlen (argv
[argc
]) + 1;
161 for ( ; envp
[envc
]; ++envc
)
162 envlen
+= strlen (envp
[envc
]) + 1;
164 result
= arglen
+ envlen
;
170 /* Pointer to target's buffer. */
171 TADDR tbuf
= sc
->arg1
;
173 int bufsize
= sc
->arg2
;
174 /* Q is the target address of where all the strings go. */
176 int word_size
= cb
->word_size
;
178 const char **argv
= cb
->init_argv
;
179 const char **envp
= cb
->init_envp
;
184 for ( ; argv
[argc
]; ++argc
)
186 int len
= strlen (argv
[argc
]);
187 int written
= (*sc
->write_mem
) (cb
, sc
, tbuf
, argv
[argc
], len
+ 1);
197 if ((*sc
->write_mem
) (cb
, sc
, tbuf
, "", 1) != 1)
207 for ( ; envp
[envc
]; ++envc
)
209 int len
= strlen (envp
[envc
]);
210 int written
= (*sc
->write_mem
) (cb
, sc
, tbuf
, envp
[envc
], len
+ 1);
220 if ((*sc
->write_mem
) (cb
, sc
, tbuf
, "", 1) != 1)
233 /* Caller must catch and handle. */
240 errcode
= get_path (cb
, sc
, sc
->arg1
, &path
);
246 result
= (*cb
->open
) (cb
, path
, sc
->arg2
/*, sc->arg3*/);
254 result
= (*cb
->close
) (cb
, sc
->arg1
);
261 /* ??? Perfect handling of error conditions may require only one
262 call to cb->read. One can't assume all the data is
263 contiguously stored in host memory so that would require
264 malloc'ing/free'ing the space. Maybe later. */
265 char buf
[FILE_XFR_SIZE
];
267 TADDR addr
= sc
->arg2
;
268 size_t count
= sc
->arg3
;
269 size_t bytes_read
= 0;
275 result
= (int) (*cb
->read_stdin
) (cb
, buf
,
276 (count
< FILE_XFR_SIZE
277 ? count
: FILE_XFR_SIZE
));
279 result
= (int) (*cb
->read
) (cb
, fd
, buf
,
280 (count
< FILE_XFR_SIZE
281 ? count
: FILE_XFR_SIZE
));
284 bytes_written
= (*sc
->write_mem
) (cb
, sc
, addr
, buf
, result
);
285 if (bytes_written
!= result
)
291 bytes_read
+= result
;
301 /* ??? Perfect handling of error conditions may require only one
302 call to cb->write. One can't assume all the data is
303 contiguously stored in host memory so that would require
304 malloc'ing/free'ing the space. Maybe later. */
305 char buf
[FILE_XFR_SIZE
];
307 TADDR addr
= sc
->arg2
;
308 size_t count
= sc
->arg3
;
310 size_t bytes_written
= 0;
314 int bytes_to_read
= count
< FILE_XFR_SIZE
? count
: FILE_XFR_SIZE
;
315 bytes_read
= (*sc
->read_mem
) (cb
, sc
, addr
, buf
, bytes_to_read
);
316 if (bytes_read
!= bytes_to_read
)
323 result
= (int) (*cb
->write_stdout
) (cb
, buf
, bytes_read
);
325 result
= (int) (*cb
->write_stderr
) (cb
, buf
, bytes_read
);
327 result
= (int) (*cb
->write
) (cb
, fd
, buf
, bytes_read
);
330 bytes_written
+= result
;
334 result
= bytes_written
;
341 unsigned long offset
= sc
->arg2
;
342 int whence
= sc
->arg3
;
344 result
= (*cb
->lseek
) (cb
, fd
, offset
, whence
);
354 errcode
= get_path (cb
, sc
, sc
->arg1
, &path
);
360 result
= (*cb
->unlink
) (cb
, path
);
372 TADDR addr
= sc
->arg2
;
374 errcode
= get_path (cb
, sc
, sc
->arg1
, &path
);
380 result
= (*cb
->stat
) (cb
, path
, &statbuf
);
384 buflen
= cb_host_to_target_stat (cb
, NULL
, NULL
);
385 buf
= xmalloc (buflen
);
386 if (cb_host_to_target_stat (cb
, &statbuf
, buf
) != buflen
)
388 /* The translation failed. This is due to an internal
389 host program error, not the target's fault. */
395 if ((*sc
->write_mem
) (cb
, sc
, addr
, buf
, buflen
) != buflen
)
411 TADDR addr
= sc
->arg2
;
413 result
= (*cb
->fstat
) (cb
, sc
->arg1
, &statbuf
);
416 buflen
= cb_host_to_target_stat (cb
, NULL
, NULL
);
417 buf
= xmalloc (buflen
);
418 if (cb_host_to_target_stat (cb
, &statbuf
, buf
) != buflen
)
420 /* The translation failed. This is due to an internal
421 host program error, not the target's fault. */
427 if ((*sc
->write_mem
) (cb
, sc
, addr
, buf
, buflen
) != buflen
)
440 /* FIXME: May wish to change CB_SYS_time to something else.
441 We might also want gettimeofday or times, but if system calls
442 can be built on others, we can keep the number we have to support
444 time_t t
= (*cb
->time
) (cb
, (time_t *) 0);
446 /* It is up to target code to process the argument to time(). */
453 /* fall through for now */
466 sc
->errcode
= cb_host_to_target_errno (cb
, errcode
);
471 sc
->errcode
= (*cb
->get_errno
) (cb
);
This page took 0.039938 seconds and 4 git commands to generate.