OLD | NEW |
1 /* Default child (native) target interface, for GDB when running under | 1 /* Default child (native) target interface, for GDB when running under |
2 Unix. | 2 Unix. |
3 | 3 |
4 Copyright (C) 1988-1996, 1998-2002, 2004-2005, 2007-2012 Free | 4 Copyright (C) 1988-1996, 1998-2002, 2004-2005, 2007-2012 Free |
5 Software Foundation, Inc. | 5 Software Foundation, Inc. |
6 | 6 |
7 This file is part of GDB. | 7 This file is part of GDB. |
8 | 8 |
9 This program is free software; you can redistribute it and/or modify | 9 This program is free software; you can redistribute it and/or modify |
10 it under the terms of the GNU General Public License as published by | 10 it under the terms of the GNU General Public License as published by |
11 the Free Software Foundation; either version 3 of the License, or | 11 the Free Software Foundation; either version 3 of the License, or |
12 (at your option) any later version. | 12 (at your option) any later version. |
13 | 13 |
14 This program is distributed in the hope that it will be useful, | 14 This program is distributed in the hope that it will be useful, |
15 but WITHOUT ANY WARRANTY; without even the implied warranty of | 15 but WITHOUT ANY WARRANTY; without even the implied warranty of |
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | 16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
17 GNU General Public License for more details. | 17 GNU General Public License for more details. |
18 | 18 |
19 You should have received a copy of the GNU General Public License | 19 You should have received a copy of the GNU General Public License |
20 along with this program. If not, see <http://www.gnu.org/licenses/>. */ | 20 along with this program. If not, see <http://www.gnu.org/licenses/>. */ |
21 | 21 |
22 #include "defs.h" | 22 #include "defs.h" |
23 #include "regcache.h" | 23 #include "regcache.h" |
24 #include "memattr.h" | 24 #include "memattr.h" |
25 #include "symtab.h" | 25 #include "symtab.h" |
26 #include "target.h" | 26 #include "target.h" |
27 #include "inferior.h" | 27 #include "inferior.h" |
28 #include "gdb_string.h" | 28 #include "gdb_string.h" |
| 29 #include "gdb_stat.h" |
29 #include "inf-child.h" | 30 #include "inf-child.h" |
| 31 #include "gdb/fileio.h" |
| 32 #include "agent.h" |
| 33 #include "gdb_wait.h" |
| 34 |
| 35 #ifdef HAVE_SYS_PARAM_H |
| 36 #include <sys/param.h> /* for MAXPATHLEN */ |
| 37 #endif |
| 38 #include <sys/types.h> |
| 39 #include <fcntl.h> |
| 40 #include <unistd.h> |
| 41 |
| 42 /* Helper function for child_wait and the derivatives of child_wait. |
| 43 HOSTSTATUS is the waitstatus from wait() or the equivalent; store our |
| 44 translation of that in OURSTATUS. */ |
| 45 void |
| 46 store_waitstatus (struct target_waitstatus *ourstatus, int hoststatus) |
| 47 { |
| 48 if (WIFEXITED (hoststatus)) |
| 49 { |
| 50 ourstatus->kind = TARGET_WAITKIND_EXITED; |
| 51 ourstatus->value.integer = WEXITSTATUS (hoststatus); |
| 52 } |
| 53 else if (!WIFSTOPPED (hoststatus)) |
| 54 { |
| 55 ourstatus->kind = TARGET_WAITKIND_SIGNALLED; |
| 56 ourstatus->value.sig = gdb_signal_from_host (WTERMSIG (hoststatus)); |
| 57 } |
| 58 else |
| 59 { |
| 60 ourstatus->kind = TARGET_WAITKIND_STOPPED; |
| 61 ourstatus->value.sig = gdb_signal_from_host (WSTOPSIG (hoststatus)); |
| 62 } |
| 63 } |
30 | 64 |
31 /* Fetch register REGNUM from the inferior. If REGNUM is -1, do this | 65 /* Fetch register REGNUM from the inferior. If REGNUM is -1, do this |
32 for all registers. */ | 66 for all registers. */ |
33 | 67 |
34 static void | 68 static void |
35 inf_child_fetch_inferior_registers (struct target_ops *ops, | 69 inf_child_fetch_inferior_registers (struct target_ops *ops, |
36 struct regcache *regcache, int regnum) | 70 struct regcache *regcache, int regnum) |
37 { | 71 { |
38 if (regnum == -1) | 72 if (regnum == -1) |
39 { | 73 { |
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
101 } | 135 } |
102 | 136 |
103 static char * | 137 static char * |
104 inf_child_pid_to_exec_file (int pid) | 138 inf_child_pid_to_exec_file (int pid) |
105 { | 139 { |
106 /* This version of Unix doesn't support translation of a process ID | 140 /* This version of Unix doesn't support translation of a process ID |
107 to the filename of the executable file. */ | 141 to the filename of the executable file. */ |
108 return NULL; | 142 return NULL; |
109 } | 143 } |
110 | 144 |
| 145 |
| 146 /* Target file operations. */ |
| 147 |
| 148 static int |
| 149 inf_child_fileio_open_flags_to_host (int fileio_open_flags, int *open_flags_p) |
| 150 { |
| 151 int open_flags = 0; |
| 152 |
| 153 if (fileio_open_flags & ~FILEIO_O_SUPPORTED) |
| 154 return -1; |
| 155 |
| 156 if (fileio_open_flags & FILEIO_O_CREAT) |
| 157 open_flags |= O_CREAT; |
| 158 if (fileio_open_flags & FILEIO_O_EXCL) |
| 159 open_flags |= O_EXCL; |
| 160 if (fileio_open_flags & FILEIO_O_TRUNC) |
| 161 open_flags |= O_TRUNC; |
| 162 if (fileio_open_flags & FILEIO_O_APPEND) |
| 163 open_flags |= O_APPEND; |
| 164 if (fileio_open_flags & FILEIO_O_RDONLY) |
| 165 open_flags |= O_RDONLY; |
| 166 if (fileio_open_flags & FILEIO_O_WRONLY) |
| 167 open_flags |= O_WRONLY; |
| 168 if (fileio_open_flags & FILEIO_O_RDWR) |
| 169 open_flags |= O_RDWR; |
| 170 /* On systems supporting binary and text mode, always open files in |
| 171 binary mode. */ |
| 172 #ifdef O_BINARY |
| 173 open_flags |= O_BINARY; |
| 174 #endif |
| 175 |
| 176 *open_flags_p = open_flags; |
| 177 return 0; |
| 178 } |
| 179 |
| 180 static int |
| 181 inf_child_errno_to_fileio_error (int errnum) |
| 182 { |
| 183 switch (errnum) |
| 184 { |
| 185 case EPERM: |
| 186 return FILEIO_EPERM; |
| 187 case ENOENT: |
| 188 return FILEIO_ENOENT; |
| 189 case EINTR: |
| 190 return FILEIO_EINTR; |
| 191 case EIO: |
| 192 return FILEIO_EIO; |
| 193 case EBADF: |
| 194 return FILEIO_EBADF; |
| 195 case EACCES: |
| 196 return FILEIO_EACCES; |
| 197 case EFAULT: |
| 198 return FILEIO_EFAULT; |
| 199 case EBUSY: |
| 200 return FILEIO_EBUSY; |
| 201 case EEXIST: |
| 202 return FILEIO_EEXIST; |
| 203 case ENODEV: |
| 204 return FILEIO_ENODEV; |
| 205 case ENOTDIR: |
| 206 return FILEIO_ENOTDIR; |
| 207 case EISDIR: |
| 208 return FILEIO_EISDIR; |
| 209 case EINVAL: |
| 210 return FILEIO_EINVAL; |
| 211 case ENFILE: |
| 212 return FILEIO_ENFILE; |
| 213 case EMFILE: |
| 214 return FILEIO_EMFILE; |
| 215 case EFBIG: |
| 216 return FILEIO_EFBIG; |
| 217 case ENOSPC: |
| 218 return FILEIO_ENOSPC; |
| 219 case ESPIPE: |
| 220 return FILEIO_ESPIPE; |
| 221 case EROFS: |
| 222 return FILEIO_EROFS; |
| 223 case ENOSYS: |
| 224 return FILEIO_ENOSYS; |
| 225 case ENAMETOOLONG: |
| 226 return FILEIO_ENAMETOOLONG; |
| 227 } |
| 228 return FILEIO_EUNKNOWN; |
| 229 } |
| 230 |
| 231 /* Open FILENAME on the target, using FLAGS and MODE. Return a |
| 232 target file descriptor, or -1 if an error occurs (and set |
| 233 *TARGET_ERRNO). */ |
| 234 static int |
| 235 inf_child_fileio_open (const char *filename, int flags, int mode, |
| 236 int *target_errno) |
| 237 { |
| 238 int nat_flags; |
| 239 int fd; |
| 240 |
| 241 if (inf_child_fileio_open_flags_to_host (flags, &nat_flags) == -1) |
| 242 { |
| 243 *target_errno = FILEIO_EINVAL; |
| 244 return -1; |
| 245 } |
| 246 |
| 247 /* We do not need to convert MODE, since the fileio protocol uses |
| 248 the standard values. */ |
| 249 fd = open (filename, nat_flags, mode); |
| 250 if (fd == -1) |
| 251 *target_errno = inf_child_errno_to_fileio_error (errno); |
| 252 |
| 253 return fd; |
| 254 } |
| 255 |
| 256 /* Write up to LEN bytes from WRITE_BUF to FD on the target. |
| 257 Return the number of bytes written, or -1 if an error occurs |
| 258 (and set *TARGET_ERRNO). */ |
| 259 static int |
| 260 inf_child_fileio_pwrite (int fd, const gdb_byte *write_buf, int len, |
| 261 ULONGEST offset, int *target_errno) |
| 262 { |
| 263 int ret; |
| 264 |
| 265 #ifdef HAVE_PWRITE |
| 266 ret = pwrite (fd, write_buf, len, (long) offset); |
| 267 #else |
| 268 ret = -1; |
| 269 #endif |
| 270 /* If we have no pwrite or it failed for this file, use lseek/write. */ |
| 271 if (ret == -1) |
| 272 { |
| 273 ret = lseek (fd, (long) offset, SEEK_SET); |
| 274 if (ret != -1) |
| 275 ret = write (fd, write_buf, len); |
| 276 } |
| 277 |
| 278 if (ret == -1) |
| 279 *target_errno = inf_child_errno_to_fileio_error (errno); |
| 280 |
| 281 return ret; |
| 282 } |
| 283 |
| 284 /* Read up to LEN bytes FD on the target into READ_BUF. |
| 285 Return the number of bytes read, or -1 if an error occurs |
| 286 (and set *TARGET_ERRNO). */ |
| 287 static int |
| 288 inf_child_fileio_pread (int fd, gdb_byte *read_buf, int len, |
| 289 ULONGEST offset, int *target_errno) |
| 290 { |
| 291 int ret; |
| 292 |
| 293 #ifdef HAVE_PREAD |
| 294 ret = pread (fd, read_buf, len, (long) offset); |
| 295 #else |
| 296 ret = -1; |
| 297 #endif |
| 298 /* If we have no pread or it failed for this file, use lseek/read. */ |
| 299 if (ret == -1) |
| 300 { |
| 301 ret = lseek (fd, (long) offset, SEEK_SET); |
| 302 if (ret != -1) |
| 303 ret = read (fd, read_buf, len); |
| 304 } |
| 305 |
| 306 if (ret == -1) |
| 307 *target_errno = inf_child_errno_to_fileio_error (errno); |
| 308 |
| 309 return ret; |
| 310 } |
| 311 |
| 312 /* Close FD on the target. Return 0, or -1 if an error occurs |
| 313 (and set *TARGET_ERRNO). */ |
| 314 static int |
| 315 inf_child_fileio_close (int fd, int *target_errno) |
| 316 { |
| 317 int ret; |
| 318 |
| 319 ret = close (fd); |
| 320 if (ret == -1) |
| 321 *target_errno = inf_child_errno_to_fileio_error (errno); |
| 322 |
| 323 return ret; |
| 324 } |
| 325 |
| 326 /* Unlink FILENAME on the target. Return 0, or -1 if an error |
| 327 occurs (and set *TARGET_ERRNO). */ |
| 328 static int |
| 329 inf_child_fileio_unlink (const char *filename, int *target_errno) |
| 330 { |
| 331 int ret; |
| 332 |
| 333 ret = unlink (filename); |
| 334 if (ret == -1) |
| 335 *target_errno = inf_child_errno_to_fileio_error (errno); |
| 336 |
| 337 return ret; |
| 338 } |
| 339 |
| 340 /* Read value of symbolic link FILENAME on the target. Return a |
| 341 null-terminated string allocated via xmalloc, or NULL if an error |
| 342 occurs (and set *TARGET_ERRNO). */ |
| 343 static char * |
| 344 inf_child_fileio_readlink (const char *filename, int *target_errno) |
| 345 { |
| 346 /* We support readlink only on systems that also provide a compile-time |
| 347 maximum path length (MAXPATHLEN), at least for now. */ |
| 348 #if defined (HAVE_READLINK) && defined (MAXPATHLEN) |
| 349 char buf[MAXPATHLEN]; |
| 350 int len; |
| 351 char *ret; |
| 352 |
| 353 len = readlink (filename, buf, sizeof buf); |
| 354 if (len < 0) |
| 355 { |
| 356 *target_errno = inf_child_errno_to_fileio_error (errno); |
| 357 return NULL; |
| 358 } |
| 359 |
| 360 ret = xmalloc (len + 1); |
| 361 memcpy (ret, buf, len); |
| 362 ret[len] = '\0'; |
| 363 return ret; |
| 364 #else |
| 365 *target_errno = FILEIO_ENOSYS; |
| 366 return NULL; |
| 367 #endif |
| 368 } |
| 369 |
| 370 static int |
| 371 inf_child_use_agent (int use) |
| 372 { |
| 373 if (agent_loaded_p ()) |
| 374 { |
| 375 use_agent = use; |
| 376 return 1; |
| 377 } |
| 378 else |
| 379 return 0; |
| 380 } |
| 381 |
| 382 static int |
| 383 inf_child_can_use_agent (void) |
| 384 { |
| 385 return agent_loaded_p (); |
| 386 } |
| 387 |
111 struct target_ops * | 388 struct target_ops * |
112 inf_child_target (void) | 389 inf_child_target (void) |
113 { | 390 { |
114 struct target_ops *t = XZALLOC (struct target_ops); | 391 struct target_ops *t = XZALLOC (struct target_ops); |
115 | 392 |
116 t->to_shortname = "child"; | 393 t->to_shortname = "child"; |
117 t->to_longname = "Unix child process"; | 394 t->to_longname = "Unix child process"; |
118 t->to_doc = "Unix child process (started by the \"run\" command)."; | 395 t->to_doc = "Unix child process (started by the \"run\" command)."; |
119 t->to_open = inf_child_open; | 396 t->to_open = inf_child_open; |
120 t->to_post_attach = inf_child_post_attach; | 397 t->to_post_attach = inf_child_post_attach; |
(...skipping 11 matching lines...) Expand all Loading... |
132 t->to_post_startup_inferior = inf_child_post_startup_inferior; | 409 t->to_post_startup_inferior = inf_child_post_startup_inferior; |
133 t->to_follow_fork = inf_child_follow_fork; | 410 t->to_follow_fork = inf_child_follow_fork; |
134 t->to_can_run = inf_child_can_run; | 411 t->to_can_run = inf_child_can_run; |
135 t->to_pid_to_exec_file = inf_child_pid_to_exec_file; | 412 t->to_pid_to_exec_file = inf_child_pid_to_exec_file; |
136 t->to_stratum = process_stratum; | 413 t->to_stratum = process_stratum; |
137 t->to_has_all_memory = default_child_has_all_memory; | 414 t->to_has_all_memory = default_child_has_all_memory; |
138 t->to_has_memory = default_child_has_memory; | 415 t->to_has_memory = default_child_has_memory; |
139 t->to_has_stack = default_child_has_stack; | 416 t->to_has_stack = default_child_has_stack; |
140 t->to_has_registers = default_child_has_registers; | 417 t->to_has_registers = default_child_has_registers; |
141 t->to_has_execution = default_child_has_execution; | 418 t->to_has_execution = default_child_has_execution; |
| 419 t->to_fileio_open = inf_child_fileio_open; |
| 420 t->to_fileio_pwrite = inf_child_fileio_pwrite; |
| 421 t->to_fileio_pread = inf_child_fileio_pread; |
| 422 t->to_fileio_close = inf_child_fileio_close; |
| 423 t->to_fileio_unlink = inf_child_fileio_unlink; |
| 424 t->to_fileio_readlink = inf_child_fileio_readlink; |
142 t->to_magic = OPS_MAGIC; | 425 t->to_magic = OPS_MAGIC; |
| 426 t->to_use_agent = inf_child_use_agent; |
| 427 t->to_can_use_agent = inf_child_can_use_agent; |
143 return t; | 428 return t; |
144 } | 429 } |
OLD | NEW |