Add a target_ops parameter to the to_kill method in struct target_ops.
[deliverable/binutils-gdb.git] / gdb / remote.c
index 8cb37faf6245ee3c88d9b610b1c327023df9b691..e3a7170bb3893644c6148de0015882c82b2e829c 100644 (file)
@@ -91,10 +91,6 @@ static void remote_files_info (struct target_ops *ignore);
 
 static void remote_prepare_to_store (struct regcache *regcache);
 
-static void remote_fetch_registers (struct regcache *regcache, int regno);
-
-static void remote_resume (ptid_t ptid, int step,
-                           enum target_signal siggnal);
 static void remote_open (char *name, int from_tty);
 
 static void extended_remote_open (char *name, int from_tty);
@@ -103,8 +99,6 @@ static void remote_open_1 (char *, int, struct target_ops *, int extended_p);
 
 static void remote_close (int quitting);
 
-static void remote_store_registers (struct regcache *regcache, int regno);
-
 static void remote_mourn (struct target_ops *ops);
 
 static void extended_remote_restart (void);
@@ -117,10 +111,7 @@ static void remote_send (char **buf, long *sizeof_buf_p);
 
 static int readchar (int timeout);
 
-static ptid_t remote_wait (ptid_t ptid,
-                          struct target_waitstatus *status);
-
-static void remote_kill (void);
+static void remote_kill (struct target_ops *ops);
 
 static int tohex (int nib);
 
@@ -144,8 +135,6 @@ static void interrupt_query (void);
 static void set_general_thread (struct ptid ptid);
 static void set_continue_thread (struct ptid ptid);
 
-static int remote_thread_alive (ptid_t);
-
 static void get_offsets (void);
 
 static void skip_frame (void);
@@ -1001,6 +990,9 @@ enum {
   PACKET_vRun,
   PACKET_QStartNoAckMode,
   PACKET_vKill,
+  PACKET_qXfer_siginfo_read,
+  PACKET_qXfer_siginfo_write,
+  PACKET_qAttached,
   PACKET_MAX
 };
 
@@ -1127,9 +1119,101 @@ static ptid_t any_thread_ptid;
 static ptid_t general_thread;
 static ptid_t continue_thread;
 
+/* Find out if the stub attached to PID (and hence GDB should offer to
+   detach instead of killing it when bailing out).  */
+
+static int
+remote_query_attached (int pid)
+{
+  struct remote_state *rs = get_remote_state ();
+
+  if (remote_protocol_packets[PACKET_qAttached].support == PACKET_DISABLE)
+    return 0;
+
+  if (remote_multi_process_p (rs))
+    sprintf (rs->buf, "qAttached:%x", pid);
+  else
+    sprintf (rs->buf, "qAttached");
+
+  putpkt (rs->buf);
+  getpkt (&rs->buf, &rs->buf_size, 0);
+
+  switch (packet_ok (rs->buf,
+                    &remote_protocol_packets[PACKET_qAttached]) == PACKET_OK)
+    {
+    case PACKET_OK:
+      if (strcmp (rs->buf, "1") == 0)
+       return 1;
+      break;
+    case PACKET_ERROR:
+      warning (_("Remote failure reply: %s"), rs->buf);
+      break;
+    case PACKET_UNKNOWN:
+      break;
+    }
+
+  return 0;
+}
+
+/* Add PID to GDB's inferior table.  Since we can be connected to a
+   remote system before before knowing about any inferior, mark the
+   target with execution when we find the first inferior.  If ATTACHED
+   is 1, then we had just attached to this inferior.  If it is 0, then
+   we just created this inferior.  If it is -1, then try querying the
+   remote stub to find out if it had attached to the inferior or
+   not.  */
+
+static struct inferior *
+remote_add_inferior (int pid, int attached)
+{
+  struct remote_state *rs = get_remote_state ();
+  struct inferior *inf;
+
+  /* Check whether this process we're learning about is to be
+     considered attached, or if is to be considered to have been
+     spawned by the stub.  */
+  if (attached == -1)
+    attached = remote_query_attached (pid);
+
+  inf = add_inferior (pid);
+
+  inf->attach_flag = attached;
+
+  /* This may be the first inferior we hear about.  */
+  if (!target_has_execution)
+    {
+      if (rs->extended)
+       target_mark_running (&extended_remote_ops);
+      else
+       target_mark_running (&remote_ops);
+    }
+
+  return inf;
+}
+
+/* Add thread PTID to GDB's thread list.  Tag it as executing/running
+   according to RUNNING.  */
+
+static void
+remote_add_thread (ptid_t ptid, int running)
+{
+  add_thread (ptid);
+
+  set_executing (ptid, running);
+  set_running (ptid, running);
+}
+
+/* Come here when we learn about a thread id from the remote target.
+   It may be the first time we hear about such thread, so take the
+   opportunity to add it to GDB's thread list.  In case this is the
+   first time we're noticing its corresponding inferior, add it to
+   GDB's inferior list as well.  */
+
 static void
-notice_new_inferiors (ptid_t currthread)
+remote_notice_new_inferior (ptid_t currthread, int running)
 {
+  struct remote_state *rs = get_remote_state ();
+
   /* If this is a new thread, add it to GDB's thread list.
      If we leave it up to WFI to do this, bad things will happen.  */
 
@@ -1137,12 +1221,14 @@ notice_new_inferiors (ptid_t currthread)
     {
       /* We're seeing an event on a thread id we knew had exited.
         This has to be a new thread reusing the old id.  Add it.  */
-      add_thread (currthread);
+      remote_add_thread (currthread, running);
       return;
     }
 
   if (!in_thread_list (currthread))
     {
+      struct inferior *inf = NULL;
+
       if (ptid_equal (pid_to_ptid (ptid_get_pid (currthread)), inferior_ptid))
        {
          /* inferior_ptid has no thread member yet.  This can happen
@@ -1170,10 +1256,16 @@ notice_new_inferiors (ptid_t currthread)
         may not know about it yet.  Add it before adding its child
         thread, so notifications are emitted in a sensible order.  */
       if (!in_inferior_list (ptid_get_pid (currthread)))
-       add_inferior (ptid_get_pid (currthread));
+       inf = remote_add_inferior (ptid_get_pid (currthread), -1);
 
       /* This is really a new thread.  Add it.  */
-      add_thread (currthread);
+      remote_add_thread (currthread, running);
+
+      /* If we found a new inferior, let the common code do whatever
+        it needs to with it (e.g., read shared libraries, insert
+        breakpoints).  */
+      if (inf != NULL)
+       notice_new_inferior (currthread, running, 0);
     }
 }
 
@@ -1192,7 +1284,7 @@ record_currthread (ptid_t currthread)
     /* We're just invalidating the local thread mirror.  */
     return;
 
-  notice_new_inferiors (currthread);
+  remote_notice_new_inferior (currthread, 0);
 }
 
 static char *last_pass_packet;
@@ -1328,7 +1420,7 @@ set_general_process (void)
     system.  */
 
 static int
-remote_thread_alive (ptid_t ptid)
+remote_thread_alive (struct target_ops *ops, ptid_t ptid)
 {
   struct remote_state *rs = get_remote_state ();
   int tid = ptid_get_tid (ptid);
@@ -2134,7 +2226,7 @@ remote_find_new_threads (void)
  */
 
 static void
-remote_threads_info (void)
+remote_threads_info (struct target_ops *ops)
 {
   struct remote_state *rs = get_remote_state ();
   char *bufp;
@@ -2155,27 +2247,15 @@ remote_threads_info (void)
              do
                {
                  new_thread = read_ptid (bufp, &bufp);
-                 if (!ptid_equal (new_thread, null_ptid)
-                     && (!in_thread_list (new_thread)
-                         || is_exited (new_thread)))
+                 if (!ptid_equal (new_thread, null_ptid))
                    {
-                     /* When connected to a multi-process aware stub,
-                        "info threads" may show up threads of
-                        inferiors we didn't know about yet.  Add them
-                        now, and before adding any of its child
-                        threads, so notifications are emitted in a
-                        sensible order.  */
-                     if (!in_inferior_list (ptid_get_pid (new_thread)))
-                       add_inferior (ptid_get_pid (new_thread));
-
-                     add_thread (new_thread);
-
                      /* In non-stop mode, we assume new found threads
-                        are running until we proven otherwise with a
+                        are running until proven otherwise with a
                         stop reply.  In all-stop, we can only get
                         here if all threads are stopped.  */
-                     set_executing (new_thread, non_stop ? 1 : 0);
-                     set_running (new_thread, non_stop ? 1 : 0);
+                     int running = non_stop ? 1 : 0;
+
+                     remote_notice_new_inferior (new_thread, running);
                    }
                }
              while (*bufp++ == ',');   /* comma-separated list */
@@ -2581,7 +2661,7 @@ remote_start_remote (struct ui_out *uiout, void *opaque)
         controlling.  We default to adding them in the running state.
         The '?' query below will then tell us about which threads are
         stopped.  */
-      remote_threads_info ();
+      remote_threads_info (args->target);
     }
   else if (rs->non_stop_aware)
     {
@@ -2614,9 +2694,6 @@ remote_start_remote (struct ui_out *uiout, void *opaque)
        }
       else
        {
-         if (args->extended_p)
-           target_mark_running (args->target);
-
          /* Save the reply for later.  */
          wait_status = alloca (strlen (rs->buf) + 1);
          strcpy (wait_status, rs->buf);
@@ -2637,7 +2714,7 @@ remote_start_remote (struct ui_out *uiout, void *opaque)
       /* Now, if we have thread information, update inferior_ptid.  */
       inferior_ptid = remote_current_thread (inferior_ptid);
 
-      add_inferior (ptid_get_pid (inferior_ptid));
+      remote_add_inferior (ptid_get_pid (inferior_ptid), -1);
 
       /* Always add the main thread.  */
       add_thread_silent (inferior_ptid);
@@ -2965,6 +3042,10 @@ static struct protocol_feature remote_protocol_features[] = {
     PACKET_QStartNoAckMode },
   { "multiprocess", PACKET_DISABLE, remote_multi_process_feature, -1 },
   { "QNonStop", PACKET_DISABLE, remote_non_stop_feature, -1 },
+  { "qXfer:siginfo:read", PACKET_DISABLE, remote_supported_packet,
+    PACKET_qXfer_siginfo_read },
+  { "qXfer:siginfo:write", PACKET_DISABLE, remote_supported_packet,
+    PACKET_qXfer_siginfo_write },
 };
 
 static void
@@ -3358,7 +3439,6 @@ extended_remote_attach_1 (struct target_ops *target, char *args, int from_tty)
   int pid;
   char *dummy;
   char *wait_status = NULL;
-  struct inferior *inf;
 
   if (!args)
     error_no_arg (_("process-id to attach"));
@@ -3399,18 +3479,16 @@ extended_remote_attach_1 (struct target_ops *target, char *args, int from_tty)
     error (_("Attaching to %s failed"),
           target_pid_to_str (pid_to_ptid (pid)));
 
-  target_mark_running (target);
   inferior_ptid = pid_to_ptid (pid);
 
   /* Now, if we have thread information, update inferior_ptid.  */
   inferior_ptid = remote_current_thread (inferior_ptid);
 
-  inf = add_inferior (pid);
-  inf->attach_flag = 1;
+  remote_add_inferior (pid, 1);
 
   if (non_stop)
     /* Get list of threads.  */
-    remote_threads_info ();
+    remote_threads_info (target);
   else
     /* Add the main thread to the thread list.  */
     add_thread_silent (inferior_ptid);
@@ -3693,7 +3771,8 @@ static enum target_signal last_sent_signal = TARGET_SIGNAL_0;
 static int last_sent_step;
 
 static void
-remote_resume (ptid_t ptid, int step, enum target_signal siggnal)
+remote_resume (struct target_ops *ops,
+              ptid_t ptid, int step, enum target_signal siggnal)
 {
   struct remote_state *rs = get_remote_state ();
   char *buf;
@@ -3948,8 +4027,8 @@ interrupt_query (void)
     }
   else
     {
-      if (query ("Interrupted while waiting for the program.\n\
-Give up (and stop debugging it)? "))
+      if (query (_("Interrupted while waiting for the program.\n\
+Give up (and stop debugging it)? ")))
        {
          pop_target ();
          deprecated_throw_reason (RETURN_QUIT);
@@ -4512,8 +4591,6 @@ process_stop_reply (struct stop_reply *stop_reply,
   if (status->kind != TARGET_WAITKIND_EXITED
       && status->kind != TARGET_WAITKIND_SIGNALLED)
     {
-      notice_new_inferiors (ptid);
-
       /* Expedited registers.  */
       if (stop_reply->regcache)
        {
@@ -4530,6 +4607,8 @@ process_stop_reply (struct stop_reply *stop_reply,
 
       remote_stopped_by_watchpoint_p = stop_reply->stopped_by_watchpoint_p;
       remote_watch_data_address = stop_reply->watch_data_address;
+
+      remote_notice_new_inferior (ptid, 0);
     }
 
   stop_reply_xfree (stop_reply);
@@ -4733,7 +4812,8 @@ remote_wait_as (ptid_t ptid, struct target_waitstatus *status)
    STATUS just as `wait' would.  */
 
 static ptid_t
-remote_wait (ptid_t ptid, struct target_waitstatus *status)
+remote_wait (struct target_ops *ops,
+            ptid_t ptid, struct target_waitstatus *status)
 {
   ptid_t event_ptid;
 
@@ -4956,7 +5036,8 @@ fetch_registers_using_g (struct regcache *regcache)
 }
 
 static void
-remote_fetch_registers (struct regcache *regcache, int regnum)
+remote_fetch_registers (struct target_ops *ops,
+                       struct regcache *regcache, int regnum)
 {
   struct remote_state *rs = get_remote_state ();
   struct remote_arch_state *rsa = get_remote_arch_state ();
@@ -5105,7 +5186,8 @@ store_registers_using_G (const struct regcache *regcache)
    of the register cache buffer.  FIXME: ignores errors.  */
 
 static void
-remote_store_registers (struct regcache *regcache, int regnum)
+remote_store_registers (struct target_ops *ops,
+                       struct regcache *regcache, int regnum)
 {
   struct remote_state *rs = get_remote_state ();
   struct remote_arch_state *rsa = get_remote_arch_state ();
@@ -5705,7 +5787,7 @@ remote_xfer_memory (CORE_ADDR mem_addr, gdb_byte *buffer, int mem_len,
    FORMAT and the remaining arguments, then gets the reply.  Returns
    whether the packet was a success, a failure, or unknown.  */
 
-enum packet_result
+static enum packet_result
 remote_send_printf (const char *format, ...)
 {
   struct remote_state *rs = get_remote_state ();
@@ -6446,7 +6528,7 @@ getpkt_or_notif_sane (char **buf, long *sizeof_buf, int forever)
 
 \f
 static void
-remote_kill (void)
+remote_kill (struct target_ops *ops)
 {
   /* Use catch_errors so the user can quit from gdb even when we
      aren't on speaking terms with the remote system.  */
@@ -6478,7 +6560,7 @@ remote_vkill (int pid, struct remote_state *rs)
 }
 
 static void
-extended_remote_kill (void)
+extended_remote_kill (struct target_ops *ops)
 {
   int res;
   int pid = ptid_get_pid (inferior_ptid);
@@ -6726,11 +6808,9 @@ extended_remote_create_inferior_1 (char *exec_file, char *args,
   /* Now, if we have thread information, update inferior_ptid.  */
   inferior_ptid = remote_current_thread (inferior_ptid);
 
-  add_inferior (ptid_get_pid (inferior_ptid));
+  remote_add_inferior (ptid_get_pid (inferior_ptid), 0);
   add_thread_silent (inferior_ptid);
 
-  target_mark_running (&extended_remote_ops);
-
   /* Get updated offsets, if the stub uses qOffsets.  */
   get_offsets ();
 }
@@ -7325,6 +7405,19 @@ remote_xfer_partial (struct target_ops *ops, enum target_object object,
                                     [PACKET_qXfer_spu_write]);
     }
 
+  /* Handle extra signal info using qxfer packets.  */
+  if (object == TARGET_OBJECT_SIGNAL_INFO)
+    {
+      if (readbuf)
+       return remote_read_qxfer (ops, "siginfo", annex, readbuf, offset, len,
+                                 &remote_protocol_packets
+                                 [PACKET_qXfer_siginfo_read]);
+      else
+       return remote_write_qxfer (ops, "siginfo", annex, writebuf, offset, len,
+                                  &remote_protocol_packets
+                                  [PACKET_qXfer_siginfo_write]);
+    }
+
   /* Only handle flash writes.  */
   if (writebuf != NULL)
     {
@@ -7769,7 +7862,7 @@ Fetch and print the remote list of thread identifiers, one pkt only"));
    buffer.  */
 
 static char *
-remote_pid_to_str (ptid_t ptid)
+remote_pid_to_str (struct target_ops *ops, ptid_t ptid)
 {
   static char buf[64];
   struct remote_state *rs = get_remote_state ();
@@ -7800,7 +7893,8 @@ remote_pid_to_str (ptid_t ptid)
    stored at OFFSET within the thread local storage for thread PTID.  */
 
 static CORE_ADDR
-remote_get_thread_local_address (ptid_t ptid, CORE_ADDR lm, CORE_ADDR offset)
+remote_get_thread_local_address (struct target_ops *ops,
+                                ptid_t ptid, CORE_ADDR lm, CORE_ADDR offset)
 {
   if (remote_protocol_packets[PACKET_qGetTLSAddr].support != PACKET_DISABLE)
     {
@@ -9071,6 +9165,12 @@ Show the maximum size of the address (in bits) in a memory packet."), NULL,
   add_packet_config_cmd (&remote_protocol_packets[PACKET_qXfer_osdata],
                         "qXfer:osdata:read", "osdata", 0);
 
+  add_packet_config_cmd (&remote_protocol_packets[PACKET_qXfer_siginfo_read],
+                         "qXfer:siginfo:read", "read-siginfo-object", 0);
+
+  add_packet_config_cmd (&remote_protocol_packets[PACKET_qXfer_siginfo_write],
+                         "qXfer:siginfo:write", "write-siginfo-object", 0);
+
   add_packet_config_cmd (&remote_protocol_packets[PACKET_qGetTLSAddr],
                         "qGetTLSAddr", "get-thread-local-storage-address",
                         0);
@@ -9108,6 +9208,9 @@ Show the maximum size of the address (in bits) in a memory packet."), NULL,
   add_packet_config_cmd (&remote_protocol_packets[PACKET_vKill],
                         "vKill", "kill", 0);
 
+  add_packet_config_cmd (&remote_protocol_packets[PACKET_qAttached],
+                        "qAttached", "query-attached", 0);
+
   /* Keep the old ``set remote Z-packet ...'' working.  Each individual
      Z sub-packet has its own set and show commands, but users may
      have sets to this variable in their .gdbinit files (or in their
This page took 0.031839 seconds and 4 git commands to generate.