a721939dabe15c0a6af6e112e747211563aff1bd
1 /* Remote target system call support.
2 Copyright 1997-2013 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 3 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 this program. If not, see <http://www.gnu.org/licenses/>. */
20 /* This interface isn't intended to be specific to any particular kind
21 of remote (hardware, simulator, whatever). As such, support for it
22 (e.g. sim/common/callback.c) should *not* live in the simulator source
23 tree, nor should it live in the gdb source tree. K&R C must be
30 #include "libiberty.h"
38 #elif defined (HAVE_STRINGS_H)
47 #include <sys/types.h>
49 #include "gdb/callback.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 /* Path to be prepended to syscalls with absolute paths, and to be
72 chdir:ed at startup, if not empty. */
73 char *simulator_sysroot
= "";
75 /* Utility of cb_syscall to fetch a path name or other string from the target.
76 The result is 0 for success or a host errno value. */
79 cb_get_string (cb
, sc
, buf
, buflen
, addr
)
88 for (p
= buf
, pend
= buf
+ buflen
; p
< pend
; ++p
, ++addr
)
90 /* No, it isn't expected that this would cause one transaction with
91 the remote target for each byte. The target could send the
92 path name along with the syscall request, and cache the file
93 name somewhere (or otherwise tweak this as desired). */
94 unsigned int count
= (*sc
->read_mem
) (cb
, sc
, addr
, p
, 1);
106 /* Utility of cb_syscall to fetch a path name.
107 The buffer is malloc'd and the address is stored in BUFP.
108 The result is that of get_string, but prepended with
109 simulator_sysroot if the string starts with '/'.
110 If an error occurs, no buffer is left malloc'd. */
113 get_path (cb
, sc
, addr
, bufp
)
119 char *buf
= xmalloc (MAX_PATH_LEN
);
121 int sysroot_len
= strlen (simulator_sysroot
);
123 result
= cb_get_string (cb
, sc
, buf
, MAX_PATH_LEN
- sysroot_len
, addr
);
126 /* Prepend absolute paths with simulator_sysroot. Relative paths
127 are supposed to be relative to a chdir within that path, but at
128 this point unknown where. */
129 if (simulator_sysroot
[0] != '\0' && *buf
== '/')
131 /* Considering expected rareness of syscalls with absolute
132 file paths (compared to relative file paths and insn
133 execution), it does not seem worthwhile to rearrange things
134 to get rid of the string moves here; we'd need at least an
135 extra call to check the initial '/' in the path. */
136 memmove (buf
+ sysroot_len
, buf
, sysroot_len
);
137 memcpy (buf
, simulator_sysroot
, sysroot_len
);
147 /* Perform a system call on behalf of the target. */
154 TWORD result
= 0, errcode
= 0;
156 if (sc
->magic
!= CB_SYSCALL_MAGIC
)
159 switch (cb_target_to_host_syscall (cb
, sc
->func
))
161 #if 0 /* FIXME: wip */
162 case CB_SYS_argvlen
:
164 /* Compute how much space is required to store the argv,envp
165 strings so that the program can allocate the space and then
166 call SYS_argv to fetch the values. */
167 int addr_size
= cb
->addr_size
;
168 int argc
,envc
,arglen
,envlen
;
169 const char **argv
= cb
->init_argv
;
170 const char **envp
= cb
->init_envp
;
175 for ( ; argv
[argc
]; ++argc
)
176 arglen
+= strlen (argv
[argc
]) + 1;
181 for ( ; envp
[envc
]; ++envc
)
182 envlen
+= strlen (envp
[envc
]) + 1;
184 result
= arglen
+ envlen
;
190 /* Pointer to target's buffer. */
191 TADDR tbuf
= sc
->arg1
;
193 int bufsize
= sc
->arg2
;
194 /* Q is the target address of where all the strings go. */
196 int word_size
= cb
->word_size
;
198 const char **argv
= cb
->init_argv
;
199 const char **envp
= cb
->init_envp
;
204 for ( ; argv
[argc
]; ++argc
)
206 int len
= strlen (argv
[argc
]);
207 int written
= (*sc
->write_mem
) (cb
, sc
, tbuf
, argv
[argc
], len
+ 1);
217 if ((*sc
->write_mem
) (cb
, sc
, tbuf
, "", 1) != 1)
227 for ( ; envp
[envc
]; ++envc
)
229 int len
= strlen (envp
[envc
]);
230 int written
= (*sc
->write_mem
) (cb
, sc
, tbuf
, envp
[envc
], len
+ 1);
240 if ((*sc
->write_mem
) (cb
, sc
, tbuf
, "", 1) != 1)
253 /* Caller must catch and handle. */
260 errcode
= get_path (cb
, sc
, sc
->arg1
, &path
);
266 result
= (*cb
->open
) (cb
, path
, sc
->arg2
/*, sc->arg3*/);
274 result
= (*cb
->close
) (cb
, sc
->arg1
);
281 /* ??? Perfect handling of error conditions may require only one
282 call to cb->read. One can't assume all the data is
283 contiguously stored in host memory so that would require
284 malloc'ing/free'ing the space. Maybe later. */
285 char buf
[FILE_XFR_SIZE
];
287 TADDR addr
= sc
->arg2
;
288 size_t count
= sc
->arg3
;
289 size_t bytes_read
= 0;
294 if (cb_is_stdin (cb
, fd
))
295 result
= (int) (*cb
->read_stdin
) (cb
, buf
,
296 (count
< FILE_XFR_SIZE
297 ? count
: FILE_XFR_SIZE
));
299 result
= (int) (*cb
->read
) (cb
, fd
, buf
,
300 (count
< FILE_XFR_SIZE
301 ? count
: FILE_XFR_SIZE
));
304 if (result
== 0) /* EOF */
306 bytes_written
= (*sc
->write_mem
) (cb
, sc
, addr
, buf
, result
);
307 if (bytes_written
!= result
)
313 bytes_read
+= result
;
316 /* If this is a short read, don't go back for more */
317 if (result
!= FILE_XFR_SIZE
)
326 /* ??? Perfect handling of error conditions may require only one
327 call to cb->write. One can't assume all the data is
328 contiguously stored in host memory so that would require
329 malloc'ing/free'ing the space. Maybe later. */
330 char buf
[FILE_XFR_SIZE
];
332 TADDR addr
= sc
->arg2
;
333 size_t count
= sc
->arg3
;
335 size_t bytes_written
= 0;
339 int bytes_to_read
= count
< FILE_XFR_SIZE
? count
: FILE_XFR_SIZE
;
340 bytes_read
= (*sc
->read_mem
) (cb
, sc
, addr
, buf
, bytes_to_read
);
341 if (bytes_read
!= bytes_to_read
)
347 if (cb_is_stdout (cb
, fd
))
349 result
= (int) (*cb
->write_stdout
) (cb
, buf
, bytes_read
);
350 (*cb
->flush_stdout
) (cb
);
352 else if (cb_is_stderr (cb
, fd
))
354 result
= (int) (*cb
->write_stderr
) (cb
, buf
, bytes_read
);
355 (*cb
->flush_stderr
) (cb
);
358 result
= (int) (*cb
->write
) (cb
, fd
, buf
, bytes_read
);
361 bytes_written
+= result
;
365 result
= bytes_written
;
372 unsigned long offset
= sc
->arg2
;
373 int whence
= sc
->arg3
;
375 result
= (*cb
->lseek
) (cb
, fd
, offset
, whence
);
385 errcode
= get_path (cb
, sc
, sc
->arg1
, &path
);
391 result
= (*cb
->unlink
) (cb
, path
);
398 case CB_SYS_truncate
:
403 errcode
= get_path (cb
, sc
, sc
->arg1
, &path
);
410 result
= (*cb
->truncate
) (cb
, path
, len
);
417 case CB_SYS_ftruncate
:
422 result
= (*cb
->ftruncate
) (cb
, fd
, len
);
432 errcode
= get_path (cb
, sc
, sc
->arg1
, &path1
);
439 errcode
= get_path (cb
, sc
, sc
->arg2
, &path2
);
447 result
= (*cb
->rename
) (cb
, path1
, path2
);
460 TADDR addr
= sc
->arg2
;
462 errcode
= get_path (cb
, sc
, sc
->arg1
, &path
);
468 result
= (*cb
->stat
) (cb
, path
, &statbuf
);
472 buflen
= cb_host_to_target_stat (cb
, NULL
, NULL
);
473 buf
= xmalloc (buflen
);
474 if (cb_host_to_target_stat (cb
, &statbuf
, buf
) != buflen
)
476 /* The translation failed. This is due to an internal
477 host program error, not the target's fault. */
483 if ((*sc
->write_mem
) (cb
, sc
, addr
, buf
, buflen
) != buflen
)
499 TADDR addr
= sc
->arg2
;
501 result
= (*cb
->fstat
) (cb
, sc
->arg1
, &statbuf
);
504 buflen
= cb_host_to_target_stat (cb
, NULL
, NULL
);
505 buf
= xmalloc (buflen
);
506 if (cb_host_to_target_stat (cb
, &statbuf
, buf
) != buflen
)
508 /* The translation failed. This is due to an internal
509 host program error, not the target's fault. */
515 if ((*sc
->write_mem
) (cb
, sc
, addr
, buf
, buflen
) != buflen
)
531 TADDR addr
= sc
->arg2
;
533 errcode
= get_path (cb
, sc
, sc
->arg1
, &path
);
539 result
= (*cb
->lstat
) (cb
, path
, &statbuf
);
544 buflen
= cb_host_to_target_stat (cb
, NULL
, NULL
);
545 buf
= xmalloc (buflen
);
546 if (cb_host_to_target_stat (cb
, &statbuf
, buf
) != buflen
)
548 /* The translation failed. This is due to an internal
549 host program error, not the target's fault.
550 Unfortunately, it's hard to test this case, so there's no
551 test-case for this execution path. */
558 if ((*sc
->write_mem
) (cb
, sc
, addr
, buf
, buflen
) != buflen
)
573 char *target_p
= xcalloc (1, cb
->target_sizeof_int
* 2);
575 result
= (*cb
->pipe
) (cb
, p
);
579 cb_store_target_endian (cb
, target_p
, cb
->target_sizeof_int
, p
[0]);
580 cb_store_target_endian (cb
, target_p
+ cb
->target_sizeof_int
,
581 cb
->target_sizeof_int
, p
[1]);
582 if ((*sc
->write_mem
) (cb
, sc
, sc
->arg1
, target_p
,
583 cb
->target_sizeof_int
* 2)
584 != cb
->target_sizeof_int
* 2)
586 /* Close the pipe fd:s. */
587 (*cb
->close
) (cb
, p
[0]);
588 (*cb
->close
) (cb
, p
[1]);
599 /* FIXME: May wish to change CB_SYS_time to something else.
600 We might also want gettimeofday or times, but if system calls
601 can be built on others, we can keep the number we have to support
603 time_t t
= (*cb
->time
) (cb
, (time_t *) 0);
605 /* It is up to target code to process the argument to time(). */
612 /* fall through for now */
625 sc
->errcode
= cb_host_to_target_errno (cb
, errcode
);
630 sc
->errcode
= (*cb
->get_errno
) (cb
);
This page took 0.056848 seconds and 4 git commands to generate.