nto-procfs.c: Add "target native".
[deliverable/binutils-gdb.git] / gdb / nto-procfs.c
index e86511c46300916ab9cac882644d53110af60f33..b328dfa99bfb19ab851917242d16520c6c0a3434 100644 (file)
 #include "command.h"
 #include "regcache.h"
 #include "solib.h"
+#include "inf-child.h"
 
 #define NULL_PID               0
 #define _DEBUG_FLAG_TRACE      (_DEBUG_FLAG_TRACE_EXEC|_DEBUG_FLAG_TRACE_RD|\
                _DEBUG_FLAG_TRACE_WR|_DEBUG_FLAG_TRACE_MODIFY)
 
-static struct target_ops procfs_ops;
-
 int ctl_fd;
 
 static void (*ofunc) ();
@@ -57,14 +56,6 @@ static procfs_run run;
 
 static void procfs_open (char *, int);
 
-static int procfs_can_run (struct target_ops *self);
-
-static int procfs_xfer_memory (CORE_ADDR, gdb_byte *, int, int,
-                              struct mem_attrib *attrib,
-                              struct target_ops *);
-
-static void init_procfs_ops (void);
-
 static ptid_t do_attach (ptid_t ptid);
 
 static int procfs_can_use_hw_breakpoint (struct target_ops *self,
@@ -606,14 +597,6 @@ procfs_files_info (struct target_ops *ignore)
                     target_pid_to_str (inferior_ptid), nto_procfs_path);
 }
 
-/* Mark our target-struct as eligible for stray "run" and "attach"
-   commands.  */
-static int
-procfs_can_run (struct target_ops *self)
-{
-  return 1;
-}
-
 /* Attach to process PID, then initialize for debugging it.  */
 static void
 procfs_attach (struct target_ops *ops, char *args, int from_tty)
@@ -849,30 +832,44 @@ procfs_fetch_registers (struct target_ops *ops,
     nto_supply_altregset (regcache, (char *) &reg.altreg);
 }
 
-/* Copy LEN bytes to/from inferior's memory starting at MEMADDR
-   from/to debugger memory starting at MYADDR.  Copy from inferior
-   if DOWRITE is zero or to inferior if DOWRITE is nonzero.
+/* Helper for procfs_xfer_partial that handles memory transfers.
+   Arguments are like target_xfer_partial.  */
 
-   Returns the length copied, which is either the LEN argument or
-   zero.  This xfer function does not do partial moves, since procfs_ops
-   doesn't allow memory operations to cross below us in the target stack
-   anyway.  */
-static int
-procfs_xfer_memory (CORE_ADDR memaddr, gdb_byte *myaddr, int len, int dowrite,
-                   struct mem_attrib *attrib, struct target_ops *target)
+static enum target_xfer_status
+procfs_xfer_memory (gdb_byte *readbuf, const gdb_byte *writebuf,
+                   ULONGEST memaddr, ULONGEST len, ULONGEST *xfered_len)
 {
-  int nbytes = 0;
+  int nbytes;
+
+  if (lseek (ctl_fd, (off_t) memaddr, SEEK_SET) != (off_t) memaddr)
+    return TARGET_XFER_E_IO;
+
+  if (writebuf != NULL)
+    nbytes = write (ctl_fd, writebuf, len);
+  else
+    nbytes = read (ctl_fd, readbuf, len);
+  if (nbytes <= 0)
+    return TARGET_XFER_E_IO;
+  *xfered_len = nbytes;
+  return TARGET_XFER_OK;
+}
+
+/* Target to_xfer_partial implementation.  */
 
-  if (lseek (ctl_fd, (off_t) memaddr, SEEK_SET) == (off_t) memaddr)
+static enum target_xfer_status
+procfs_xfer_partial (struct target_ops *ops, enum target_object object,
+                    const char *annex, gdb_byte *readbuf,
+                    const gdb_byte *writebuf, ULONGEST offset, ULONGEST len,
+                    ULONGEST *xfered_len)
+{
+  switch (object)
     {
-      if (dowrite)
-       nbytes = write (ctl_fd, myaddr, len);
-      else
-       nbytes = read (ctl_fd, myaddr, len);
-      if (nbytes < 0)
-       nbytes = 0;
+    case TARGET_OBJECT_MEMORY:
+      return procfs_xfer_memory (readbuf, writebuf, offset, len, xfered_len);
+    default:
+      return ops->beneath->to_xfer_partial (ops->beneath, object, annex,
+                                           readbuf, writebuf, offset, len);
     }
-  return (nbytes);
 }
 
 /* Take a program previously attached to and detaches it.
@@ -907,7 +904,7 @@ procfs_detach (struct target_ops *ops, const char *args, int from_tty)
   inferior_ptid = null_ptid;
   detach_inferior (pid);
   init_thread_list ();
-  unpush_target (&procfs_ops); /* Pop out of handling an inferior.  */
+  unpush_target (ops); /* Pop out of handling an inferior.  */
 }
 
 static int
@@ -947,7 +944,8 @@ procfs_insert_hw_breakpoint (struct target_ops *self, struct gdbarch *gdbarch,
 }
 
 static int
-procfs_remove_hw_breakpoint (struct gdbarch *gdbarch,
+procfs_remove_hw_breakpoint (struct target_ops *self,
+                            struct gdbarch *gdbarch,
                             struct bp_target_info *bp_tgt)
 {
   return procfs_breakpoint (bp_tgt->placed_address,
@@ -1025,7 +1023,7 @@ procfs_mourn_inferior (struct target_ops *ops)
     }
   inferior_ptid = null_ptid;
   init_thread_list ();
-  unpush_target (&procfs_ops);
+  unpush_target (ops);
   generic_mourn_inferior ();
 }
 
@@ -1218,7 +1216,7 @@ procfs_create_inferior (struct target_ops *ops, char *exec_file,
 }
 
 static void
-procfs_stop (ptid_t ptid)
+procfs_stop (struct target_ops *self, ptid_t ptid)
 {
   devctl (ctl_fd, DCMD_PROC_STOP, NULL, 0, 0);
 }
@@ -1229,13 +1227,6 @@ procfs_kill_inferior (struct target_ops *ops)
   target_mourn_inferior ();
 }
 
-/* Store register REGNO, or all registers if REGNO == -1, from the contents
-   of REGISTERS.  */
-static void
-procfs_prepare_to_store (struct target_ops *self, struct regcache *regcache)
-{
-}
-
 /* Fill buf with regset and return devctl cmd to do the setting.  Return
    -1 if we fail to get the regset.  Store size of regset in regsize.  */
 static int
@@ -1336,7 +1327,8 @@ procfs_store_registers (struct target_ops *ops,
 /* Set list of signals to be handled in the target.  */
 
 static void
-procfs_pass_signals (int numsigs, unsigned char *pass_signals)
+procfs_pass_signals (struct target_ops *self,
+                    int numsigs, unsigned char *pass_signals)
 {
   int signo;
 
@@ -1378,56 +1370,70 @@ procfs_pid_to_str (struct target_ops *ops, ptid_t ptid)
   return buf;
 }
 
+/* to_can_run implementation for "target procfs".  Note this really
+  means "can this target be the default run target", which there can
+  be only one, and we make it be "target native" like other ports.
+  "target procfs <node>" wouldn't make sense as default run target, as
+  it needs <node>.  */
+
+static int
+procfs_can_run (struct target_ops *self)
+{
+  return 0;
+}
+
+/* "target procfs".  */
+static struct target_ops nto_procfs_ops;
+
+/* Create the "native" and "procfs" targets.  */
+
 static void
-init_procfs_ops (void)
+init_procfs_targets (void)
 {
-  procfs_ops.to_shortname = "procfs";
-  procfs_ops.to_longname = "QNX Neutrino procfs child process";
-  procfs_ops.to_doc =
-    "QNX Neutrino procfs child process (started by the \"run\" command).\n\
-       target procfs <node>";
-  procfs_ops.to_open = procfs_open;
-  procfs_ops.to_attach = procfs_attach;
-  procfs_ops.to_post_attach = procfs_post_attach;
-  procfs_ops.to_detach = procfs_detach;
-  procfs_ops.to_resume = procfs_resume;
-  procfs_ops.to_wait = procfs_wait;
-  procfs_ops.to_fetch_registers = procfs_fetch_registers;
-  procfs_ops.to_store_registers = procfs_store_registers;
-  procfs_ops.to_prepare_to_store = procfs_prepare_to_store;
-  procfs_ops.deprecated_xfer_memory = procfs_xfer_memory;
-  procfs_ops.to_files_info = procfs_files_info;
-  procfs_ops.to_insert_breakpoint = procfs_insert_breakpoint;
-  procfs_ops.to_remove_breakpoint = procfs_remove_breakpoint;
-  procfs_ops.to_can_use_hw_breakpoint = procfs_can_use_hw_breakpoint;
-  procfs_ops.to_insert_hw_breakpoint = procfs_insert_hw_breakpoint;
-  procfs_ops.to_remove_hw_breakpoint = procfs_remove_breakpoint;
-  procfs_ops.to_insert_watchpoint = procfs_insert_hw_watchpoint;
-  procfs_ops.to_remove_watchpoint = procfs_remove_hw_watchpoint;
-  procfs_ops.to_stopped_by_watchpoint = procfs_stopped_by_watchpoint;
-  procfs_ops.to_terminal_init = terminal_init_inferior;
-  procfs_ops.to_terminal_inferior = terminal_inferior;
-  procfs_ops.to_terminal_ours_for_output = terminal_ours_for_output;
-  procfs_ops.to_terminal_ours = terminal_ours;
-  procfs_ops.to_terminal_info = child_terminal_info;
-  procfs_ops.to_kill = procfs_kill_inferior;
-  procfs_ops.to_create_inferior = procfs_create_inferior;
-  procfs_ops.to_mourn_inferior = procfs_mourn_inferior;
-  procfs_ops.to_can_run = procfs_can_run;
-  procfs_ops.to_pass_signals = procfs_pass_signals;
-  procfs_ops.to_thread_alive = procfs_thread_alive;
-  procfs_ops.to_find_new_threads = procfs_find_new_threads;
-  procfs_ops.to_pid_to_str = procfs_pid_to_str;
-  procfs_ops.to_stop = procfs_stop;
-  procfs_ops.to_stratum = process_stratum;
-  procfs_ops.to_has_all_memory = default_child_has_all_memory;
-  procfs_ops.to_has_memory = default_child_has_memory;
-  procfs_ops.to_has_stack = default_child_has_stack;
-  procfs_ops.to_has_registers = default_child_has_registers;
-  procfs_ops.to_has_execution = default_child_has_execution;
-  procfs_ops.to_magic = OPS_MAGIC;
-  procfs_ops.to_have_continuable_watchpoint = 1;
-  procfs_ops.to_extra_thread_info = nto_extra_thread_info;
+  struct target_ops *t = inf_child_target ();
+
+  /* Leave to_shortname as "native".  */
+  t->to_longname = "QNX Neutrino local process";
+  t->to_doc = "QNX Neutrino local process (started by the \"run\" command).";
+  t->to_open = procfs_open;
+  t->to_attach = procfs_attach;
+  t->to_post_attach = procfs_post_attach;
+  t->to_detach = procfs_detach;
+  t->to_resume = procfs_resume;
+  t->to_wait = procfs_wait;
+  t->to_fetch_registers = procfs_fetch_registers;
+  t->to_store_registers = procfs_store_registers;
+  t->to_xfer_partial = procfs_xfer_partial;
+  t->to_files_info = procfs_files_info;
+  t->to_insert_breakpoint = procfs_insert_breakpoint;
+  t->to_remove_breakpoint = procfs_remove_breakpoint;
+  t->to_can_use_hw_breakpoint = procfs_can_use_hw_breakpoint;
+  t->to_insert_hw_breakpoint = procfs_insert_hw_breakpoint;
+  t->to_remove_hw_breakpoint = procfs_remove_hw_breakpoint;
+  t->to_insert_watchpoint = procfs_insert_hw_watchpoint;
+  t->to_remove_watchpoint = procfs_remove_hw_watchpoint;
+  t->to_stopped_by_watchpoint = procfs_stopped_by_watchpoint;
+  t->to_kill = procfs_kill_inferior;
+  t->to_create_inferior = procfs_create_inferior;
+  t->to_mourn_inferior = procfs_mourn_inferior;
+  t->to_pass_signals = procfs_pass_signals;
+  t->to_thread_alive = procfs_thread_alive;
+  t->to_find_new_threads = procfs_find_new_threads;
+  t->to_pid_to_str = procfs_pid_to_str;
+  t->to_stop = procfs_stop;
+  t->to_have_continuable_watchpoint = 1;
+  t->to_extra_thread_info = nto_extra_thread_info;
+
+  /* Register "target native".  This is the default run target.  */
+  add_target (t);
+
+  /* Register "target procfs <node>".  */
+  nto_procfs_ops = *t;
+  nto_procfs_ops.to_shortname = "procfs";
+  nto_procfs_ops.to_can_run = procfs_can_run;
+  t->to_longname = "QNX Neutrino local or remote process";
+  t->to_doc = "QNX Neutrino process.  target procfs <node>";
+  add_target (&nto_procfs_ops);
 }
 
 #define OSTYPE_NTO 1
@@ -1437,8 +1443,7 @@ _initialize_procfs (void)
 {
   sigset_t set;
 
-  init_procfs_ops ();
-  add_target (&procfs_ops);
+  init_procfs_targets ();
 
   /* We use SIGUSR1 to gain control after we block waiting for a process.
      We use sigwaitevent to wait.  */
This page took 0.027281 seconds and 4 git commands to generate.