* gdbthread.h (struct thread_info): Add comments around
[deliverable/binutils-gdb.git] / gdb / remote.c
index 8a28eb9cb5e4fddd79d2124686466ce46c06e30b..3433e9d2ffed5f77b0035722b76e77c234df376e 100644 (file)
@@ -59,6 +59,7 @@
 
 #include "remote-fileio.h"
 #include "gdb/fileio.h"
+#include "gdb_stat.h"
 
 #include "memory-map.h"
 
@@ -92,23 +93,17 @@ 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_async_resume (ptid_t ptid, int step,
-                                enum target_signal siggnal);
 static void remote_open (char *name, int from_tty);
-static void remote_async_open (char *name, int from_tty);
 
 static void extended_remote_open (char *name, int from_tty);
-static void extended_remote_async_open (char *name, int from_tty);
 
-static void remote_open_1 (char *, int, struct target_ops *, int extended_p,
-                          int async_p);
+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 (void);
-static void remote_async_mourn (void);
 
 static void extended_remote_restart (void);
 
@@ -121,15 +116,21 @@ 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 ptid_t remote_async_wait (ptid_t ptid,
-                                       struct target_waitstatus *status);
+                          struct target_waitstatus *status);
 
 static void remote_kill (void);
-static void remote_async_kill (void);
 
 static int tohex (int nib);
 
+static int remote_can_async_p (void);
+
+static int remote_is_async_p (void);
+
+static void remote_async (void (*callback) (enum inferior_event_type event_type,
+                                           void *context), void *context);
+
+static int remote_async_mask (int new_mask);
+
 static void remote_detach (char *args, int from_tty);
 
 static void remote_interrupt (int signo);
@@ -138,7 +139,8 @@ static void remote_interrupt_twice (int signo);
 
 static void interrupt_query (void);
 
-static void set_thread (int, int);
+static void set_general_thread (struct ptid ptid);
+static void set_continue_thread (struct ptid ptid);
 
 static int remote_thread_alive (ptid_t);
 
@@ -154,7 +156,7 @@ static void init_remote_ops (void);
 
 static void init_extended_remote_ops (void);
 
-static void remote_stop (void);
+static void remote_stop (ptid_t);
 
 static int ishex (int ch, int *val);
 
@@ -180,7 +182,7 @@ static ptid_t remote_current_thread (ptid_t oldptid);
 
 static void remote_find_new_threads (void);
 
-static void record_currthread (int currthread);
+static void record_currthread (ptid_t currthread);
 
 static int fromhex (int a);
 
@@ -246,6 +248,11 @@ struct remote_state
      skip calling getpkt.  This flag is set when BUF contains a
      stop reply packet and the target is not waiting.  */
   int cached_wait_status;
+
+  /* True, if in no ack mode.  That is, neither GDB nor the stub will
+     expect acks from each other.  The connection is assumed to be
+     reliable.  */
+  int noack_mode;
 };
 
 /* This data could be associated with a target, but we do not always
@@ -268,9 +275,9 @@ struct packet_reg
   long regnum; /* GDB's internal register number.  */
   LONGEST pnum; /* Remote protocol register number.  */
   int in_g_packet; /* Always part of G packet.  */
-  /* long size in bytes;  == register_size (current_gdbarch, regnum);
+  /* long size in bytes;  == register_size (target_gdbarch, regnum);
      at present.  */
-  /* char *name; == gdbarch_register_name (current_gdbarch, regnum);
+  /* char *name; == gdbarch_register_name (target_gdbarch, regnum);
      at present.  */
 };
 
@@ -303,7 +310,7 @@ static struct gdbarch_data *remote_gdbarch_data_handle;
 static struct remote_arch_state *
 get_remote_arch_state (void)
 {
-  return gdbarch_data (current_gdbarch, remote_gdbarch_data_handle);
+  return gdbarch_data (target_gdbarch, remote_gdbarch_data_handle);
 }
 
 /* Fetch the global remote target state.  */
@@ -439,7 +446,7 @@ get_remote_packet_size (void)
 static struct packet_reg *
 packet_reg_from_regnum (struct remote_arch_state *rsa, long regnum)
 {
-  if (regnum < 0 && regnum >= gdbarch_num_regs (current_gdbarch))
+  if (regnum < 0 && regnum >= gdbarch_num_regs (target_gdbarch))
     return NULL;
   else
     {
@@ -453,7 +460,7 @@ static struct packet_reg *
 packet_reg_from_pnum (struct remote_arch_state *rsa, LONGEST pnum)
 {
   int i;
-  for (i = 0; i < gdbarch_num_regs (current_gdbarch); i++)
+  for (i = 0; i < gdbarch_num_regs (target_gdbarch); i++)
     {
       struct packet_reg *r = &rsa->regs[i];
       if (r->pnum == pnum)
@@ -477,14 +484,8 @@ static struct target_ops remote_ops;
 
 static struct target_ops extended_remote_ops;
 
-/* Temporary target ops. Just like the remote_ops and
-   extended_remote_ops, but with asynchronous support.  */
-static struct target_ops remote_async_ops;
-
 static int remote_async_mask_value = 1;
 
-static struct target_ops extended_async_remote_ops;
-
 /* FIXME: cagney/1999-09-23: Even though getpkt was called with
    ``forever'' still use the normal timeout mechanism.  This is
    currently used by the ASYNC code to guarentee that target reads
@@ -520,8 +521,8 @@ static struct serial *remote_desc = NULL;
 
 static int remote_address_size;
 
-/* Tempoary to track who currently owns the terminal.  See
-   target_async_terminal_* for more details.  */
+/* Temporary to track who currently owns the terminal.  See
+   remote_terminal_* for more details.  */
 
 static int remote_async_terminal_ours_p;
 
@@ -938,6 +939,7 @@ enum {
   PACKET_qSearch_memory,
   PACKET_vAttach,
   PACKET_vRun,
+  PACKET_QStartNoAckMode,
   PACKET_MAX
 };
 
@@ -1042,11 +1044,16 @@ static struct async_signal_handler *sigint_remote_token;
 
 \f
 
+static ptid_t magic_null_ptid;
+static ptid_t not_sent_ptid;
+static ptid_t any_thread_ptid;
+
+/* These are the threads which we last sent to the remote system.  The
+   TID member will be -1 for all or -2 for not sent yet.  */
+
+static ptid_t general_thread;
+static ptid_t continue_thread;
 
-/* These are the threads which we last sent to the remote system.
-   -1 for all or -2 for not sent yet.  */
-static int general_thread;
-static int continue_thread;
 
 /* Call this function as a result of
    1) A halt indication (T packet) containing a thread id
@@ -1055,14 +1062,38 @@ static int continue_thread;
  */
 
 static void
-record_currthread (int currthread)
+record_currthread (ptid_t currthread)
 {
   general_thread = currthread;
 
   /* 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.  */
-  if (!in_thread_list (pid_to_ptid (currthread)))
-    add_thread (pid_to_ptid (currthread));
+  if (!in_thread_list (currthread))
+    {
+      if (ptid_equal (pid_to_ptid (ptid_get_pid (currthread)), inferior_ptid))
+       {
+         /* inferior_ptid has no thread member yet.  This can happen
+            with the vAttach -> remote_wait,"TAAthread:" path if the
+            stub doesn't support qC.  This is the first stop reported
+            after an attach, so this is the main thread.  Update the
+            ptid in the thread list.  */
+         struct thread_info *th = find_thread_pid (inferior_ptid);
+         inferior_ptid = th->ptid = currthread;
+       }
+      else if (ptid_equal (magic_null_ptid, inferior_ptid))
+       {
+         /* inferior_ptid is not set yet.  This can happen with the
+            vRun -> remote_wait,"TAAthread:" path if the stub
+            doesn't support qC.  This is the first stop reported
+            after an attach, so this is the main thread.  Update the
+            ptid in the thread list.  */
+         struct thread_info *th = find_thread_pid (inferior_ptid);
+         inferior_ptid = th->ptid = currthread;
+       }
+      else
+       /* This is really a new thread.  Add it.  */
+       add_thread (currthread);
+    }
 }
 
 static char *last_pass_packet;
@@ -1124,44 +1155,76 @@ remote_pass_signals (void)
     }
 }
 
-#define MAGIC_NULL_PID 42000
-
+/* If PTID is MAGIC_NULL_PTID, don't set any thread.  If PTID is
+   MINUS_ONE_PTID, set the thread to -1, so the stub returns the
+   thread.  If GEN is set, set the general thread, if not, then set
+   the step/continue thread.  */
 static void
-set_thread (int th, int gen)
+set_thread (struct ptid ptid, int gen)
 {
   struct remote_state *rs = get_remote_state ();
+  ptid_t state = gen ? general_thread : continue_thread;
   char *buf = rs->buf;
-  int state = gen ? general_thread : continue_thread;
+  char *endbuf = rs->buf + get_remote_packet_size ();
 
-  if (state == th)
+  if (ptid_equal (state, ptid))
     return;
 
-  buf[0] = 'H';
-  buf[1] = gen ? 'g' : 'c';
-  if (th == MAGIC_NULL_PID)
+  *buf++ = 'H';
+  *buf++ = gen ? 'g' : 'c';
+  if (ptid_equal (ptid, magic_null_ptid))
+    xsnprintf (buf, endbuf - buf, "0");
+  else if (ptid_equal (ptid, any_thread_ptid))
+    xsnprintf (buf, endbuf - buf, "0");
+  else if (ptid_equal (ptid, minus_one_ptid))
+    xsnprintf (buf, endbuf - buf, "-1");
+  else
     {
-      buf[2] = '0';
-      buf[3] = '\0';
+      int tid = ptid_get_tid (ptid);
+      if (tid < 0)
+       xsnprintf (buf, endbuf - buf, "-%x", -tid);
+      else
+       xsnprintf (buf, endbuf - buf, "%x", tid);
     }
-  else if (th < 0)
-    xsnprintf (&buf[2], get_remote_packet_size () - 2, "-%x", -th);
-  else
-    xsnprintf (&buf[2], get_remote_packet_size () - 2, "%x", th);
-  putpkt (buf);
+  putpkt (rs->buf);
   getpkt (&rs->buf, &rs->buf_size, 0);
   if (gen)
-    general_thread = th;
+    general_thread = ptid;
   else
-    continue_thread = th;
+    continue_thread = ptid;
 }
+
+static void
+set_general_thread (struct ptid ptid)
+{
+  set_thread (ptid, 1);
+}
+
+static void
+set_continue_thread (struct ptid ptid)
+{
+  set_thread (ptid, 0);
+}
+
 \f
-/*  Return nonzero if the thread TH is still alive on the remote system.  */
+/*  Return nonzero if the thread PTID is still alive on the remote
+    system.  */
 
 static int
 remote_thread_alive (ptid_t ptid)
 {
   struct remote_state *rs = get_remote_state ();
-  int tid = PIDGET (ptid);
+  int tid = ptid_get_tid (ptid);
+
+  if (ptid_equal (ptid, magic_null_ptid))
+    /* The main thread is always alive.  */
+    return 1;
+
+  if (ptid_get_pid (ptid) != 0 && ptid_get_tid (ptid) == 0)
+    /* The main thread is always alive.  This can happen after a
+       vAttach, if the remote side doesn't support
+       multi-threading.  */
+    return 1;
 
   if (tid < 0)
     xsnprintf (rs->buf, get_remote_packet_size (), "T-%08x", -tid);
@@ -1781,7 +1844,7 @@ remote_get_threadlist (int startflag, threadref *nextthread, int result_limit,
 
 /* remote_find_new_threads retrieves the thread list and for each
    thread in the list, looks up the thread in GDB's internal list,
-   ading the thread if it does not already exist.  This involves
+   adding the thread if it does not already exist.  This involves
    getting partial thread lists from the remote target so, polling the
    quit_flag is required.  */
 
@@ -1832,9 +1895,8 @@ remote_threadlist_iterator (rmt_thread_action stepfunction, void *context,
 static int
 remote_newthread_step (threadref *ref, void *context)
 {
-  ptid_t ptid;
-
-  ptid = pid_to_ptid (threadref_to_int (ref));
+  int pid = ptid_get_pid (inferior_ptid);
+  ptid_t ptid = ptid_build (pid, 0, threadref_to_int (ref));
 
   if (!in_thread_list (ptid))
     add_thread (ptid);
@@ -1847,16 +1909,23 @@ static ptid_t
 remote_current_thread (ptid_t oldpid)
 {
   struct remote_state *rs = get_remote_state ();
+  char *p = rs->buf;
+  int tid;
+  int pid;
 
   putpkt ("qC");
   getpkt (&rs->buf, &rs->buf_size, 0);
   if (rs->buf[0] == 'Q' && rs->buf[1] == 'C')
-    /* Use strtoul here, so we'll correctly parse values whose highest
-       bit is set.  The protocol carries them as a simple series of
-       hex digits; in the absence of a sign, strtol will see such
-       values as positive numbers out of range for signed 'long', and
-       return LONG_MAX to indicate an overflow.  */
-    return pid_to_ptid (strtoul (&rs->buf[2], NULL, 16));
+    {
+      /* Use strtoul here, so we'll correctly parse values whose
+        highest bit is set.  The protocol carries them as a simple
+        series of hex digits; in the absence of a sign, strtol will
+        see such values as positive numbers out of range for signed
+        'long', and return LONG_MAX to indicate an overflow.  */
+      tid = strtoul (&rs->buf[2], NULL, 16);
+      pid = ptid_get_pid (oldpid);
+      return ptid_build (pid, 0, tid);
+    }
   else
     return oldpid;
 }
@@ -1870,8 +1939,6 @@ remote_find_new_threads (void)
 {
   remote_threadlist_iterator (remote_newthread_step, 0,
                              CRAZY_MAX_THREADS);
-  if (PIDGET (inferior_ptid) == MAGIC_NULL_PID)        /* ack ack ack */
-    inferior_ptid = remote_current_thread (inferior_ptid);
 }
 
 /*
@@ -1887,6 +1954,8 @@ remote_threads_info (void)
   struct remote_state *rs = get_remote_state ();
   char *bufp;
   int tid;
+  int pid;
+  ptid_t new_thread;
 
   if (remote_desc == 0)                /* paranoia */
     error (_("Command can only be used when connected to the remote target."));
@@ -1909,8 +1978,10 @@ remote_threads_info (void)
                     positive numbers out of range for signed 'long',
                     and return LONG_MAX to indicate an overflow.  */
                  tid = strtoul (bufp, &bufp, 16);
-                 if (tid != 0 && !in_thread_list (pid_to_ptid (tid)))
-                   add_thread (pid_to_ptid (tid));
+                 pid = ptid_get_pid (inferior_ptid);
+                 new_thread = ptid_build (pid, 0, tid);
+                 if (tid != 0 && !in_thread_list (new_thread))
+                   add_thread (new_thread);
                }
              while (*bufp++ == ',');   /* comma-separated list */
              putpkt ("qsThreadInfo");
@@ -1951,10 +2022,16 @@ remote_threads_extra_info (struct thread_info *tp)
     internal_error (__FILE__, __LINE__,
                    _("remote_threads_extra_info"));
 
+  if (ptid_equal (tp->ptid, magic_null_ptid)
+      || (ptid_get_pid (tp->ptid) != 0 && ptid_get_tid (tp->ptid) == 0))
+    /* This is the main thread which was added by GDB.  The remote
+       server doesn't know about it.  */
+    return NULL;
+
   if (use_threadextra_query)
     {
-      xsnprintf (rs->buf, get_remote_packet_size (), "qThreadExtraInfo,%x",
-                PIDGET (tp->ptid));
+      xsnprintf (rs->buf, get_remote_packet_size (), "qThreadExtraInfo,%lx",
+                ptid_get_tid (tp->ptid));
       putpkt (rs->buf);
       getpkt (&rs->buf, &rs->buf_size, 0);
       if (rs->buf[0] != 0)
@@ -1970,7 +2047,7 @@ remote_threads_extra_info (struct thread_info *tp)
   use_threadextra_query = 0;
   set = TAG_THREADID | TAG_EXISTS | TAG_THREADNAME
     | TAG_MOREDISPLAY | TAG_DISPLAY;
-  int_to_threadref (&id, PIDGET (tp->ptid));
+  int_to_threadref (&id, ptid_get_tid (tp->ptid));
   if (remote_get_threadinfo (&id, set, &threadinfo))
     if (threadinfo.active)
       {
@@ -2134,6 +2211,16 @@ get_offsets (void)
       segments[1] = data->segment_bases[1] + data_addr;
       num_segments = 2;
     }
+  /* If the object file has only one segment, assume that it is text
+     rather than data; main programs with no writable data are rare,
+     but programs with no code are useless.  Of course the code might
+     have ended up in the data segment... to detect that we would need
+     the permissions here.  */
+  else if (data && data->num_segments == 1)
+    {
+      segments[0] = data->segment_bases[0] + text_addr;
+      num_segments = 1;
+    }
   /* There's no way to relocate by segment.  */
   else
     do_segments = 0;
@@ -2190,9 +2277,6 @@ remote_start_remote (struct ui_out *uiout, void *opaque)
 
   immediate_quit++;            /* Allow user to interrupt it.  */
 
-  /* Ack any packet which the remote side has already sent.  */
-  serial_write (remote_desc, "+", 1);
-
   /* Check whether the target is running now.  */
   putpkt ("?");
   getpkt (&rs->buf, &rs->buf_size, 0);
@@ -2219,8 +2303,11 @@ remote_start_remote (struct ui_out *uiout, void *opaque)
       strcpy (wait_status, rs->buf);
     }
 
+  /* Start afresh.  */
+  init_thread_list ();
+
   /* Let the stub know that we want it to return the thread.  */
-  set_thread (-1, 0);
+  set_continue_thread (minus_one_ptid);
 
   /* Without this, some commands which require an active target
      (such as kill) won't work.  This variable serves (at least)
@@ -2229,11 +2316,14 @@ remote_start_remote (struct ui_out *uiout, void *opaque)
      These functions should be split out into seperate variables,
      especially since GDB will someday have a notion of debugging
      several processes.  */
-  inferior_ptid = pid_to_ptid (MAGIC_NULL_PID);
+  inferior_ptid = magic_null_ptid;
 
   /* Now, if we have thread information, update inferior_ptid.  */
   inferior_ptid = remote_current_thread (inferior_ptid);
 
+  /* Always add the main thread.  */
+  add_thread_silent (inferior_ptid);
+
   get_offsets ();              /* Get text, data & bss offsets.  */
 
   /* Use the previously fetched status.  */
@@ -2251,14 +2341,7 @@ remote_start_remote (struct ui_out *uiout, void *opaque)
 static void
 remote_open (char *name, int from_tty)
 {
-  remote_open_1 (name, from_tty, &remote_ops, 0, 0);
-}
-
-/* Just like remote_open, but with asynchronous support.  */
-static void
-remote_async_open (char *name, int from_tty)
-{
-  remote_open_1 (name, from_tty, &remote_async_ops, 0, 1);
+  remote_open_1 (name, from_tty, &remote_ops, 0);
 }
 
 /* Open a connection to a remote debugger using the extended
@@ -2267,16 +2350,7 @@ remote_async_open (char *name, int from_tty)
 static void
 extended_remote_open (char *name, int from_tty)
 {
-  remote_open_1 (name, from_tty, &extended_remote_ops, 1 /*extended_p */,
-                0 /* async_p */);
-}
-
-/* Just like extended_remote_open, but with asynchronous support.  */
-static void
-extended_remote_async_open (char *name, int from_tty)
-{
-  remote_open_1 (name, from_tty, &extended_async_remote_ops,
-                1 /*extended_p */, 1 /* async_p */);
+  remote_open_1 (name, from_tty, &extended_remote_ops, 1 /*extended_p */);
 }
 
 /* Generic code for opening a connection to a remote target.  */
@@ -2327,7 +2401,7 @@ remote_check_symbols (struct objfile *objfile)
 
          /* If this is a function address, return the start of code
             instead of any data function descriptor.  */
-         sym_addr = gdbarch_convert_from_func_ptr_addr (current_gdbarch,
+         sym_addr = gdbarch_convert_from_func_ptr_addr (target_gdbarch,
                                                         sym_addr,
                                                         &current_target);
 
@@ -2460,6 +2534,8 @@ static struct protocol_feature remote_protocol_features[] = {
     PACKET_qXfer_spu_write },
   { "QPassSignals", PACKET_DISABLE, remote_supported_packet,
     PACKET_QPassSignals },
+  { "QStartNoAckMode", PACKET_DISABLE, remote_supported_packet,
+    PACKET_QStartNoAckMode },
 };
 
 static void
@@ -2590,17 +2666,18 @@ remote_query_supported (void)
 
 
 static void
-remote_open_1 (char *name, int from_tty, struct target_ops *target,
-              int extended_p, int async_p)
+remote_open_1 (char *name, int from_tty, struct target_ops *target, int extended_p)
 {
   struct remote_state *rs = get_remote_state ();
+  struct packet_config *noack_config;
+
   if (name == 0)
     error (_("To open a remote debug connection, you need to specify what\n"
           "serial device is attached to the remote system\n"
           "(e.g. /dev/ttyS0, /dev/ttya, COM1, etc.)."));
 
   /* See FIXME above.  */
-  if (!async_p)
+  if (!target_async_permitted)
     wait_forever_enabled_p = 1;
 
   /* If we're connected to a running target, target_preopen will kill it.
@@ -2675,24 +2752,53 @@ remote_open_1 (char *name, int from_tty, struct target_ops *target,
      remote_query_supported or as they are needed.  */
   init_all_packet_configs ();
   rs->explicit_packet_size = 0;
+  rs->noack_mode = 0;
 
-  general_thread = -2;
-  continue_thread = -2;
+  general_thread = not_sent_ptid;
+  continue_thread = not_sent_ptid;
 
   /* Probe for ability to use "ThreadInfo" query, as required.  */
   use_threadinfo_query = 1;
   use_threadextra_query = 1;
 
+  /* Ack any packet which the remote side has already sent.  */
+  serial_write (remote_desc, "+", 1);
+
   /* The first packet we send to the target is the optional "supported
      packets" request.  If the target can answer this, it will tell us
      which later probes to skip.  */
   remote_query_supported ();
 
+  /* Next, we possibly activate noack mode.
+
+     If the QStartNoAckMode packet configuration is set to AUTO,
+     enable noack mode if the stub reported a wish for it with
+     qSupported.
+
+     If set to TRUE, then enable noack mode even if the stub didn't
+     report it in qSupported.  If the stub doesn't reply OK, the
+     session ends with an error.
+
+     If FALSE, then don't activate noack mode, regardless of what the
+     stub claimed should be the default with qSupported.  */
+
+  noack_config = &remote_protocol_packets[PACKET_QStartNoAckMode];
+
+  if (noack_config->detect == AUTO_BOOLEAN_TRUE
+      || (noack_config->detect == AUTO_BOOLEAN_AUTO
+         && noack_config->support == PACKET_ENABLE))
+    {
+      putpkt ("QStartNoAckMode");
+      getpkt (&rs->buf, &rs->buf_size, 0);
+      if (packet_ok (rs->buf, noack_config) == PACKET_OK)
+       rs->noack_mode = 1;
+    }
+
   /* Next, if the target can specify a description, read it.  We do
      this before anything involving memory or registers.  */
   target_find_description ();
 
-  if (async_p)
+  if (target_async_permitted)
     {
       /* With this target we start out by owning the terminal.  */
       remote_async_terminal_ours_p = 1;
@@ -2737,13 +2843,13 @@ remote_open_1 (char *name, int from_tty, struct target_ops *target,
     if (ex.reason < 0)
       {
        pop_target ();
-       if (async_p)
+       if (target_async_permitted)
          wait_forever_enabled_p = 1;
        throw_exception (ex);
       }
   }
 
-  if (async_p)
+  if (target_async_permitted)
     wait_forever_enabled_p = 1;
 
   if (extended_p)
@@ -2877,6 +2983,13 @@ extended_remote_attach_1 (struct target_ops *target, char *args, int from_tty)
 
   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);
+
+  /* Now, add the main thread to the thread list.  */
+  add_thread_silent (inferior_ptid);
+
   attach_flag = 1;
 
   /* Next, if the target can specify a description, read it.  We do
@@ -2895,12 +3008,6 @@ extended_remote_attach (char *args, int from_tty)
   extended_remote_attach_1 (&extended_remote_ops, args, from_tty);
 }
 
-static void
-extended_async_remote_attach (char *args, int from_tty)
-{
-  extended_remote_attach_1 (&extended_async_remote_ops, args, from_tty);
-}
-
 /* Convert hex digit A to a number.  */
 
 static int
@@ -3012,10 +3119,10 @@ remote_vcont_probe (struct remote_state *rs)
 
 /* Resume the remote inferior by using a "vCont" packet.  The thread
    to be resumed is PTID; STEP and SIGGNAL indicate whether the
-   resumed thread should be single-stepped and/or signalled.  If PTID's
-   PID is -1, then all threads are resumed; the thread to be stepped and/or
-   signalled is given in the global INFERIOR_PTID.  This function returns
-   non-zero iff it resumes the inferior.
+   resumed thread should be single-stepped and/or signalled.  If PTID
+   equals minus_one_ptid, then all threads are resumed; the thread to
+   be stepped and/or signalled is given in the global INFERIOR_PTID.
+   This function returns non-zero iff it resumes the inferior.
 
    This function issues a strict subset of all possible vCont commands at the
    moment.  */
@@ -3024,7 +3131,6 @@ static int
 remote_vcont_resume (ptid_t ptid, int step, enum target_signal siggnal)
 {
   struct remote_state *rs = get_remote_state ();
-  int pid = PIDGET (ptid);
   char *outbuf;
   struct cleanup *old_cleanup;
 
@@ -3038,11 +3144,12 @@ remote_vcont_resume (ptid_t ptid, int step, enum target_signal siggnal)
      about overflowing BUF.  Should there be a generic
      "multi-part-packet" packet?  */
 
-  if (PIDGET (inferior_ptid) == MAGIC_NULL_PID)
+  if (ptid_equal (ptid, magic_null_ptid))
     {
-      /* MAGIC_NULL_PTID means that we don't have any active threads, so we
-        don't have any PID numbers the inferior will understand.  Make sure
-        to only send forms that do not specify a PID.  */
+      /* MAGIC_NULL_PTID means that we don't have any active threads,
+        so we don't have any TID numbers the inferior will
+        understand.  Make sure to only send forms that do not specify
+        a TID.  */
       if (step && siggnal != TARGET_SIGNAL_0)
        outbuf = xstrprintf ("vCont;S%02x", siggnal);
       else if (step)
@@ -3052,31 +3159,31 @@ remote_vcont_resume (ptid_t ptid, int step, enum target_signal siggnal)
       else
        outbuf = xstrprintf ("vCont;c");
     }
-  else if (pid == -1)
+  else if (ptid_equal (ptid, minus_one_ptid))
     {
       /* Resume all threads, with preference for INFERIOR_PTID.  */
+      int tid = ptid_get_tid (inferior_ptid);
       if (step && siggnal != TARGET_SIGNAL_0)
-       outbuf = xstrprintf ("vCont;S%02x:%x;c", siggnal,
-                            PIDGET (inferior_ptid));
+       outbuf = xstrprintf ("vCont;S%02x:%x;c", siggnal, tid);
       else if (step)
-       outbuf = xstrprintf ("vCont;s:%x;c", PIDGET (inferior_ptid));
+       outbuf = xstrprintf ("vCont;s:%x;c", tid);
       else if (siggnal != TARGET_SIGNAL_0)
-       outbuf = xstrprintf ("vCont;C%02x:%x;c", siggnal,
-                            PIDGET (inferior_ptid));
+       outbuf = xstrprintf ("vCont;C%02x:%x;c", siggnal, tid);
       else
        outbuf = xstrprintf ("vCont;c");
     }
   else
     {
       /* Scheduler locking; resume only PTID.  */
+      int tid = ptid_get_tid (ptid);
       if (step && siggnal != TARGET_SIGNAL_0)
-       outbuf = xstrprintf ("vCont;S%02x:%x", siggnal, pid);
+       outbuf = xstrprintf ("vCont;S%02x:%x", siggnal, tid);
       else if (step)
-       outbuf = xstrprintf ("vCont;s:%x", pid);
+       outbuf = xstrprintf ("vCont;s:%x", tid);
       else if (siggnal != TARGET_SIGNAL_0)
-       outbuf = xstrprintf ("vCont;C%02x:%x", siggnal, pid);
+       outbuf = xstrprintf ("vCont;C%02x:%x", siggnal, tid);
       else
-       outbuf = xstrprintf ("vCont;c:%x", pid);
+       outbuf = xstrprintf ("vCont;c:%x", tid);
     }
 
   gdb_assert (outbuf && strlen (outbuf) < get_remote_packet_size ());
@@ -3100,7 +3207,6 @@ remote_resume (ptid_t ptid, int step, enum target_signal siggnal)
 {
   struct remote_state *rs = get_remote_state ();
   char *buf;
-  int pid = PIDGET (ptid);
 
   last_sent_signal = siggnal;
   last_sent_step = step;
@@ -3110,13 +3216,14 @@ remote_resume (ptid_t ptid, int step, enum target_signal siggnal)
 
   /* The vCont packet doesn't need to specify threads via Hc.  */
   if (remote_vcont_resume (ptid, step, siggnal))
-    return;
+    goto done;
 
-  /* All other supported resume packets do use Hc, so call set_thread.  */
-  if (pid == -1)
-    set_thread (0, 0);         /* Run any thread.  */
+  /* All other supported resume packets do use Hc, so set the continue
+     thread.  */
+  if (ptid_equal (ptid, minus_one_ptid))
+    set_continue_thread (any_thread_ptid);
   else
-    set_thread (pid, 0);       /* Run this thread.  */
+    set_continue_thread (ptid);
 
   buf = rs->buf;
   if (siggnal != TARGET_SIGNAL_0)
@@ -3130,14 +3237,8 @@ remote_resume (ptid_t ptid, int step, enum target_signal siggnal)
     strcpy (buf, step ? "s" : "c");
 
   putpkt (buf);
-}
-
-/* Same as remote_resume, but with async support.  */
-static void
-remote_async_resume (ptid_t ptid, int step, enum target_signal siggnal)
-{
-  remote_resume (ptid, step, siggnal);
 
+ done:
   /* We are about to start executing the inferior, let's register it
      with the event loop. NOTE: this is the one place where all the
      execution commands end up. We could alternatively do this in each
@@ -3147,13 +3248,6 @@ remote_async_resume (ptid_t ptid, int step, enum target_signal siggnal)
      NOT asynchronously.  */
   if (target_can_async_p ())
     target_async (inferior_event_handler, 0);
-  /* Tell the world that the target is now executing.  */
-  /* FIXME: cagney/1999-09-23: Is it the targets responsibility to set
-     this?  Instead, should the client of target just assume (for
-     async targets) that the target is going to start executing?  Is
-     this information already found in the continuation block?  */
-  if (target_is_async_p ())
-    target_executing = 1;
 }
 \f
 
@@ -3191,7 +3285,7 @@ async_remote_interrupt (gdb_client_data arg)
   if (remote_debug)
     fprintf_unfiltered (gdb_stdlog, "remote_interrupt called\n");
 
-  target_stop ();
+  target_stop (inferior_ptid);
 }
 
 /* Perform interrupt, if the first attempt did not succeed. Just give
@@ -3245,7 +3339,7 @@ remote_interrupt_twice (int signo)
    interrupt is requested, either by the command line or the GUI, we
    will eventually end up here.  */
 static void
-remote_stop (void)
+remote_stop (ptid_t ptid)
 {
   /* Send a break or a ^C, depending on user preference.  */
   if (remote_debug)
@@ -3281,8 +3375,12 @@ Give up (and stop debugging it)? "))
    is required.  */
 
 static void
-remote_async_terminal_inferior (void)
+remote_terminal_inferior (void)
 {
+  if (!target_async_permitted)
+    /* Nothing to do.  */
+    return;
+
   /* FIXME: cagney/1999-09-27: Shouldn't need to test for
      sync_execution here.  This function should only be called when
      GDB is resuming the inferior in the forground.  A background
@@ -3307,12 +3405,16 @@ remote_async_terminal_inferior (void)
 }
 
 static void
-remote_async_terminal_ours (void)
+remote_terminal_ours (void)
 {
-  /* See FIXME in remote_async_terminal_inferior.  */
+  if (!target_async_permitted)
+    /* Nothing to do.  */
+    return;
+
+  /* See FIXME in remote_terminal_inferior.  */
   if (!sync_execution)
     return;
-  /* See FIXME in remote_async_terminal_inferior.  */
+  /* See FIXME in remote_terminal_inferior.  */
   if (remote_async_terminal_ours_p)
     return;
   cleanup_sigint_signal_handler (NULL);
@@ -3320,10 +3422,6 @@ remote_async_terminal_ours (void)
   remote_async_terminal_ours_p = 1;
 }
 
-/* If nonzero, ignore the next kill.  */
-
-int kill_kludge;
-
 void
 remote_console_output (char *msg)
 {
@@ -3341,9 +3439,7 @@ remote_console_output (char *msg)
 }
 
 /* Wait until the remote machine stops, then return,
-   storing status in STATUS just as `wait' would.
-   Returns "pid", which in the case of a multi-threaded
-   remote OS, is the thread-id.  */
+   storing status in STATUS just as `wait' would.  */
 
 static ptid_t
 remote_wait (ptid_t ptid, struct target_waitstatus *status)
@@ -3351,233 +3447,13 @@ remote_wait (ptid_t ptid, struct target_waitstatus *status)
   struct remote_state *rs = get_remote_state ();
   struct remote_arch_state *rsa = get_remote_arch_state ();
   ULONGEST thread_num = -1;
+  ULONGEST process_num = -1;
   ULONGEST addr;
   int solibs_changed = 0;
 
   status->kind = TARGET_WAITKIND_EXITED;
   status->value.integer = 0;
 
-  while (1)
-    {
-      char *buf, *p;
-
-      if (rs->cached_wait_status)
-       /* Use the cached wait status, but only once.  */
-       rs->cached_wait_status = 0;
-      else
-       {
-         ofunc = signal (SIGINT, remote_interrupt);
-         /* If the user hit C-c before this packet, or between packets,
-            pretend that it was hit right here.  */
-         if (quit_flag)
-           {
-             quit_flag = 0;
-             remote_interrupt (SIGINT);
-           }
-         getpkt (&rs->buf, &rs->buf_size, 1);
-         signal (SIGINT, ofunc);
-       }
-
-      buf = rs->buf;
-
-      remote_stopped_by_watchpoint_p = 0;
-
-      switch (buf[0])
-       {
-       case 'E':               /* Error of some sort.  */
-         /* We're out of sync with the target now.  Did it continue or not?
-            Not is more likely, so report a stop.  */
-         warning (_("Remote failure reply: %s"), buf);
-         status->kind = TARGET_WAITKIND_STOPPED;
-         status->value.sig = TARGET_SIGNAL_0;
-         goto got_status;
-       case 'F':               /* File-I/O request.  */
-         remote_fileio_request (buf);
-         continue;
-       case 'T':               /* Status with PC, SP, FP, ...  */
-         {
-           gdb_byte regs[MAX_REGISTER_SIZE];
-
-           /* Expedited reply, containing Signal, {regno, reg} repeat.  */
-           /*  format is:  'Tssn...:r...;n...:r...;n...:r...;#cc', where
-              ss = signal number
-              n... = register number
-              r... = register contents
-            */
-           p = &buf[3];        /* after Txx */
-
-           while (*p)
-             {
-               char *p1;
-               char *p_temp;
-               int fieldsize;
-               LONGEST pnum = 0;
-
-               /* If the packet contains a register number save it in
-                  pnum and set p1 to point to the character following
-                  it.  Otherwise p1 points to p.  */
-
-               /* If this packet is an awatch packet, don't parse the
-                  'a' as a register number.  */
-
-               if (strncmp (p, "awatch", strlen("awatch")) != 0)
-                 {
-                   /* Read the ``P'' register number.  */
-                   pnum = strtol (p, &p_temp, 16);
-                   p1 = p_temp;
-                 }
-               else
-                 p1 = p;
-
-               if (p1 == p)    /* No register number present here.  */
-                 {
-                   p1 = strchr (p, ':');
-                   if (p1 == NULL)
-                     error (_("Malformed packet(a) (missing colon): %s\n\
-Packet: '%s'\n"),
-                            p, buf);
-                   if (strncmp (p, "thread", p1 - p) == 0)
-                     {
-                       p_temp = unpack_varlen_hex (++p1, &thread_num);
-                       record_currthread (thread_num);
-                       p = p_temp;
-                     }
-                   else if ((strncmp (p, "watch", p1 - p) == 0)
-                            || (strncmp (p, "rwatch", p1 - p) == 0)
-                            || (strncmp (p, "awatch", p1 - p) == 0))
-                     {
-                       remote_stopped_by_watchpoint_p = 1;
-                       p = unpack_varlen_hex (++p1, &addr);
-                       remote_watch_data_address = (CORE_ADDR)addr;
-                     }
-                   else if (strncmp (p, "library", p1 - p) == 0)
-                     {
-                       p1++;
-                       p_temp = p1;
-                       while (*p_temp && *p_temp != ';')
-                         p_temp++;
-
-                       solibs_changed = 1;
-                       p = p_temp;
-                     }
-                   else
-                     {
-                       /* Silently skip unknown optional info.  */
-                       p_temp = strchr (p1 + 1, ';');
-                       if (p_temp)
-                         p = p_temp;
-                     }
-                 }
-               else
-                 {
-                   struct packet_reg *reg = packet_reg_from_pnum (rsa, pnum);
-                   p = p1;
-
-                   if (*p++ != ':')
-                     error (_("Malformed packet(b) (missing colon): %s\n\
-Packet: '%s'\n"),
-                            p, buf);
-
-                   if (reg == NULL)
-                     error (_("Remote sent bad register number %s: %s\n\
-Packet: '%s'\n"),
-                            phex_nz (pnum, 0), p, buf);
-
-                   fieldsize = hex2bin (p, regs,
-                                        register_size (current_gdbarch,
-                                                       reg->regnum));
-                   p += 2 * fieldsize;
-                   if (fieldsize < register_size (current_gdbarch,
-                                                  reg->regnum))
-                     warning (_("Remote reply is too short: %s"), buf);
-                   regcache_raw_supply (get_current_regcache (),
-                                        reg->regnum, regs);
-                 }
-
-               if (*p++ != ';')
-                 error (_("Remote register badly formatted: %s\nhere: %s"),
-                        buf, p);
-             }
-         }
-         /* fall through */
-       case 'S':               /* Old style status, just signal only.  */
-         if (solibs_changed)
-           status->kind = TARGET_WAITKIND_LOADED;
-         else
-           {
-             status->kind = TARGET_WAITKIND_STOPPED;
-             status->value.sig = (enum target_signal)
-               (((fromhex (buf[1])) << 4) + (fromhex (buf[2])));
-           }
-
-         if (buf[3] == 'p')
-           {
-             thread_num = strtol ((const char *) &buf[4], NULL, 16);
-             record_currthread (thread_num);
-           }
-         goto got_status;
-       case 'W':               /* Target exited.  */
-         {
-           /* The remote process exited.  */
-           status->kind = TARGET_WAITKIND_EXITED;
-           status->value.integer = (fromhex (buf[1]) << 4) + fromhex (buf[2]);
-           goto got_status;
-         }
-       case 'X':
-         status->kind = TARGET_WAITKIND_SIGNALLED;
-         status->value.sig = (enum target_signal)
-           (((fromhex (buf[1])) << 4) + (fromhex (buf[2])));
-         kill_kludge = 1;
-
-         goto got_status;
-       case 'O':               /* Console output.  */
-         remote_console_output (buf + 1);
-         continue;
-       case '\0':
-         if (last_sent_signal != TARGET_SIGNAL_0)
-           {
-             /* Zero length reply means that we tried 'S' or 'C' and
-                the remote system doesn't support it.  */
-             target_terminal_ours_for_output ();
-             printf_filtered
-               ("Can't send signals to this remote system.  %s not sent.\n",
-                target_signal_to_name (last_sent_signal));
-             last_sent_signal = TARGET_SIGNAL_0;
-             target_terminal_inferior ();
-
-             strcpy ((char *) buf, last_sent_step ? "s" : "c");
-             putpkt ((char *) buf);
-             continue;
-           }
-         /* else fallthrough */
-       default:
-         warning (_("Invalid remote reply: %s"), buf);
-         continue;
-       }
-    }
-got_status:
-  if (thread_num != -1)
-    {
-      return pid_to_ptid (thread_num);
-    }
-  return inferior_ptid;
-}
-
-/* Async version of remote_wait.  */
-static ptid_t
-remote_async_wait (ptid_t ptid, struct target_waitstatus *status)
-{
-  struct remote_state *rs = get_remote_state ();
-  struct remote_arch_state *rsa = get_remote_arch_state ();
-  ULONGEST thread_num = -1;
-  ULONGEST addr;
-  int solibs_changed = 0;
-
-  status->kind = TARGET_WAITKIND_EXITED;
-  status->value.integer = 0;
-
-  remote_stopped_by_watchpoint_p = 0;
-
   while (1)
     {
       char *buf, *p;
@@ -3609,6 +3485,8 @@ remote_async_wait (ptid_t ptid, struct target_waitstatus *status)
 
       buf = rs->buf;
 
+      remote_stopped_by_watchpoint_p = 0;
+
       switch (buf[0])
        {
        case 'E':               /* Error of some sort.  */
@@ -3638,18 +3516,18 @@ remote_async_wait (ptid_t ptid, struct target_waitstatus *status)
                char *p1;
                char *p_temp;
                int fieldsize;
-               long pnum = 0;
+               LONGEST pnum = 0;
 
                /* If the packet contains a register number, save it
                   in pnum and set p1 to point to the character
                   following it.  Otherwise p1 points to p.  */
 
-               /* If this packet is an awatch packet, don't parse the 'a'
-                  as a register number.  */
+               /* If this packet is an awatch packet, don't parse the
+                  'a' as a register number.  */
 
                if (strncmp (p, "awatch", strlen("awatch")) != 0)
                  {
-                   /* Read the register number.  */
+                   /* Read the ``P'' register number.  */
                    pnum = strtol (p, &p_temp, 16);
                    p1 = p_temp;
                  }
@@ -3666,7 +3544,6 @@ Packet: '%s'\n"),
                    if (strncmp (p, "thread", p1 - p) == 0)
                      {
                        p_temp = unpack_varlen_hex (++p1, &thread_num);
-                       record_currthread (thread_num);
                        p = p_temp;
                      }
                    else if ((strncmp (p, "watch", p1 - p) == 0)
@@ -3695,35 +3572,37 @@ Packet: '%s'\n"),
                          p = p_temp;
                      }
                  }
-
                else
                  {
                    struct packet_reg *reg = packet_reg_from_pnum (rsa, pnum);
                    p = p1;
-                   if (*p++ != ':')
+
+                   if (*p != ':')
                      error (_("Malformed packet(b) (missing colon): %s\n\
 Packet: '%s'\n"),
                             p, buf);
+                    ++p;
 
                    if (reg == NULL)
-                     error (_("Remote sent bad register number %ld: %s\n\
+                     error (_("Remote sent bad register number %s: %s\n\
 Packet: '%s'\n"),
-                            pnum, p, buf);
+                            phex_nz (pnum, 0), p, buf);
 
                    fieldsize = hex2bin (p, regs,
-                                        register_size (current_gdbarch,
+                                        register_size (target_gdbarch,
                                                        reg->regnum));
                    p += 2 * fieldsize;
-                   if (fieldsize < register_size (current_gdbarch,
+                   if (fieldsize < register_size (target_gdbarch,
                                                   reg->regnum))
                      warning (_("Remote reply is too short: %s"), buf);
                    regcache_raw_supply (get_current_regcache (),
                                         reg->regnum, regs);
                  }
 
-               if (*p++ != ';')
+               if (*p != ';')
                  error (_("Remote register badly formatted: %s\nhere: %s"),
                         buf, p);
+                ++p;
              }
          }
          /* fall through */
@@ -3736,12 +3615,6 @@ Packet: '%s'\n"),
              status->value.sig = (enum target_signal)
                (((fromhex (buf[1])) << 4) + (fromhex (buf[2])));
            }
-
-         if (buf[3] == 'p')
-           {
-             thread_num = strtol ((const char *) &buf[4], NULL, 16);
-             record_currthread (thread_num);
-           }
          goto got_status;
        case 'W':               /* Target exited.  */
          {
@@ -3754,15 +3627,19 @@ Packet: '%s'\n"),
          status->kind = TARGET_WAITKIND_SIGNALLED;
          status->value.sig = (enum target_signal)
            (((fromhex (buf[1])) << 4) + (fromhex (buf[2])));
-         kill_kludge = 1;
 
          goto got_status;
        case 'O':               /* Console output.  */
          remote_console_output (buf + 1);
-         /* Return immediately to the event loop. The event loop will
-             still be waiting on the inferior afterwards.  */
-          status->kind = TARGET_WAITKIND_IGNORE;
-          goto got_status;
+         if (target_can_async_p ())
+           {
+             /* Return immediately to the event loop. The event loop
+                will still be waiting on the inferior afterwards.  */
+             status->kind = TARGET_WAITKIND_IGNORE;
+             goto got_status;
+           }
+         else
+           continue;
        case '\0':
          if (last_sent_signal != TARGET_SIGNAL_0)
            {
@@ -3788,8 +3665,12 @@ Packet: '%s'\n"),
 got_status:
   if (thread_num != -1)
     {
-      return pid_to_ptid (thread_num);
+      ptid_t ptid;
+      ptid = ptid_build (ptid_get_pid (inferior_ptid), 0, thread_num);
+      record_currthread (ptid);
+      return ptid;
     }
+
   return inferior_ptid;
 }
 
@@ -3992,7 +3873,7 @@ remote_fetch_registers (struct regcache *regcache, int regnum)
   struct remote_arch_state *rsa = get_remote_arch_state ();
   int i;
 
-  set_thread (PIDGET (inferior_ptid), 1);
+  set_general_thread (inferior_ptid);
 
   if (regnum >= 0)
     {
@@ -4141,7 +4022,7 @@ remote_store_registers (struct regcache *regcache, int regnum)
   struct remote_arch_state *rsa = get_remote_arch_state ();
   int i;
 
-  set_thread (PIDGET (inferior_ptid), 1);
+  set_general_thread (inferior_ptid);
 
   if (regnum >= 0)
     {
@@ -4225,7 +4106,7 @@ remote_address_masked (CORE_ADDR addr)
   int address_size = remote_address_size;
   /* If "remoteaddresssize" was not set, default to target address size.  */
   if (!address_size)
-    address_size = gdbarch_addr_bit (current_gdbarch);
+    address_size = gdbarch_addr_bit (target_gdbarch);
 
   if (address_size > 0
       && address_size < (sizeof (ULONGEST) * 8))
@@ -4918,6 +4799,11 @@ putpkt_binary (char *buf, int cnt)
       if (serial_write (remote_desc, buf2, p - buf2))
        perror_with_name (_("putpkt: write failed"));
 
+      /* If this is a no acks version of the remote protocol, send the
+        packet and move on.  */
+      if (rs->noack_mode)
+        break;
+
       /* Read until either a timeout occurs (-2) or '+' is read.  */
       while (1)
        {
@@ -4994,6 +4880,7 @@ putpkt_binary (char *buf, int cnt)
        }
 #endif
     }
+  return 0;
 }
 
 /* Come here after finding the start of a frame when we expected an
@@ -5049,6 +4936,7 @@ read_frame (char **buf_p,
   long bc;
   int c;
   char *buf = *buf_p;
+  struct remote_state *rs = get_remote_state ();
 
   csum = 0;
   bc = 0;
@@ -5094,6 +4982,12 @@ read_frame (char **buf_p,
                return -1;
              }
 
+           /* Don't recompute the checksum; with no ack packets we
+              don't have any way to indicate a packet retransmission
+              is necessary.  */
+           if (rs->noack_mode)
+             return bc;
+
            pktcsum = (fromhex (check_0) << 4) | fromhex (check_1);
            if (csum == pktcsum)
               return bc;
@@ -5252,61 +5146,38 @@ getpkt_sane (char **buf, long *sizeof_buf, int forever)
              fputstrn_unfiltered (*buf, val, 0, gdb_stdlog);
              fprintf_unfiltered (gdb_stdlog, "\n");
            }
-         serial_write (remote_desc, "+", 1);
+
+         /* Skip the ack char if we're in no-ack mode.  */
+         if (!rs->noack_mode)
+           serial_write (remote_desc, "+", 1);
          return val;
        }
 
       /* Try the whole thing again.  */
     retry:
-      serial_write (remote_desc, "-", 1);
+      /* Skip the nack char if we're in no-ack mode.  */
+      if (!rs->noack_mode)
+       serial_write (remote_desc, "-", 1);
     }
 
   /* We have tried hard enough, and just can't receive the packet.
      Give up.  */
 
   printf_unfiltered (_("Ignoring packet error, continuing...\n"));
-  serial_write (remote_desc, "+", 1);
+
+  /* Skip the ack char if we're in no-ack mode.  */
+  if (!rs->noack_mode)
+    serial_write (remote_desc, "+", 1);
   return -1;
 }
 \f
 static void
 remote_kill (void)
-{
-  /* For some mysterious reason, wait_for_inferior calls kill instead of
-     mourn after it gets TARGET_WAITKIND_SIGNALLED.  Work around it.  */
-  if (kill_kludge)
-    {
-      kill_kludge = 0;
-      target_mourn_inferior ();
-      return;
-    }
-
-  /* Use catch_errors so the user can quit from gdb even when we aren't on
-     speaking terms with the remote system.  */
-  catch_errors ((catch_errors_ftype *) putpkt, "k", "", RETURN_MASK_ERROR);
-
-  /* Don't wait for it to die.  I'm not really sure it matters whether
-     we do or not.  For the existing stubs, kill is a noop.  */
-  target_mourn_inferior ();
-}
-
-/* Async version of remote_kill.  */
-static void
-remote_async_kill (void)
 {
   /* Unregister the file descriptor from the event loop.  */
   if (target_is_async_p ())
     serial_async (remote_desc, NULL, 0);
 
-  /* For some mysterious reason, wait_for_inferior calls kill instead of
-     mourn after it gets TARGET_WAITKIND_SIGNALLED.  Work around it.  */
-  if (kill_kludge)
-    {
-      kill_kludge = 0;
-      target_mourn_inferior ();
-      return;
-    }
-
   /* Use catch_errors so the user can quit from gdb even when we
      aren't on speaking terms with the remote system.  */
   catch_errors ((catch_errors_ftype *) putpkt, "k", "", RETURN_MASK_ERROR);
@@ -5322,12 +5193,6 @@ remote_mourn (void)
   remote_mourn_1 (&remote_ops);
 }
 
-static void
-remote_async_mourn (void)
-{
-  remote_mourn_1 (&remote_async_ops);
-}
-
 /* Worker function for remote_mourn.  */
 static void
 remote_mourn_1 (struct target_ops *target)
@@ -5357,7 +5222,8 @@ extended_remote_mourn_1 (struct target_ops *target)
       /* Assume that the target has been restarted.  Set inferior_ptid
         so that bits of core GDB realizes there's something here, e.g.,
         so that the user can say "kill" again.  */
-      inferior_ptid = pid_to_ptid (MAGIC_NULL_PID);
+      inferior_ptid = remote_current_thread (magic_null_ptid);
+      add_thread_silent (inferior_ptid);
     }
   else
     {
@@ -5373,12 +5239,6 @@ extended_remote_mourn (void)
   extended_remote_mourn_1 (&extended_remote_ops);
 }
 
-static void
-extended_async_remote_mourn (void)
-{
-  extended_remote_mourn_1 (&extended_async_remote_ops);
-}
-
 static int
 extended_remote_run (char *args)
 {
@@ -5448,12 +5308,11 @@ extended_remote_run (char *args)
 
 static void
 extended_remote_create_inferior_1 (char *exec_file, char *args,
-                                  char **env, int from_tty,
-                                  int async_p)
+                                  char **env, int from_tty)
 {
   /* If running asynchronously, register the target file descriptor
      with the event loop.  */
-  if (async_p && target_can_async_p ())
+  if (target_can_async_p ())
     target_async (inferior_event_handler, 0);
 
   /* Now restart the remote server.  */
@@ -5478,11 +5337,11 @@ extended_remote_create_inferior_1 (char *exec_file, char *args,
 
   /* Now mark the inferior as running before we do anything else.  */
   attach_flag = 0;
-  inferior_ptid = pid_to_ptid (MAGIC_NULL_PID);
-  if (async_p)
-    target_mark_running (&extended_async_remote_ops);
-  else
-    target_mark_running (&extended_remote_ops);
+  inferior_ptid = magic_null_ptid;
+
+  add_thread_silent (inferior_ptid);
+
+  target_mark_running (&extended_remote_ops);
 
   /* Get updated offsets, if the stub uses qOffsets.  */
   get_offsets ();
@@ -5492,14 +5351,7 @@ static void
 extended_remote_create_inferior (char *exec_file, char *args,
                                 char **env, int from_tty)
 {
-  extended_remote_create_inferior_1 (exec_file, args, env, from_tty, 0);
-}
-
-static void
-extended_remote_async_create_inferior (char *exec_file, char *args,
-                                      char **env, int from_tty)
-{
-  extended_remote_create_inferior_1 (exec_file, args, env, from_tty, 1);
+  extended_remote_create_inferior_1 (exec_file, args, env, from_tty);
 }
 \f
 
@@ -5517,12 +5369,12 @@ remote_insert_breakpoint (struct bp_target_info *bp_tgt)
 
   if (remote_protocol_packets[PACKET_Z0].support != PACKET_DISABLE)
     {
-      CORE_ADDR addr;
+      CORE_ADDR addr = bp_tgt->placed_address;
       struct remote_state *rs;
       char *p;
+      int bpsize;
 
-      gdbarch_breakpoint_from_pc
-       (current_gdbarch, &bp_tgt->placed_address, &bp_tgt->placed_size);
+      gdbarch_breakpoint_from_pc (target_gdbarch, &addr, &bpsize);
 
       rs = get_remote_state ();
       p = rs->buf;
@@ -5530,9 +5382,9 @@ remote_insert_breakpoint (struct bp_target_info *bp_tgt)
       *(p++) = 'Z';
       *(p++) = '0';
       *(p++) = ',';
-      addr = (ULONGEST) remote_address_masked (bp_tgt->placed_address);
+      addr = (ULONGEST) remote_address_masked (addr);
       p += hexnumstr (p, addr);
-      sprintf (p, ",%d", bp_tgt->placed_size);
+      sprintf (p, ",%d", bpsize);
 
       putpkt (rs->buf);
       getpkt (&rs->buf, &rs->buf_size, 0);
@@ -5542,6 +5394,8 @@ remote_insert_breakpoint (struct bp_target_info *bp_tgt)
        case PACKET_ERROR:
          return -1;
        case PACKET_OK:
+         bp_tgt->placed_address = addr;
+         bp_tgt->placed_size = bpsize;
          return 0;
        case PACKET_UNKNOWN:
          break;
@@ -5722,7 +5576,7 @@ remote_insert_hw_breakpoint (struct bp_target_info *bp_tgt)
      instruction, even though we aren't inserting one ourselves.  */
 
   gdbarch_breakpoint_from_pc
-    (current_gdbarch, &bp_tgt->placed_address, &bp_tgt->placed_size);
+    (target_gdbarch, &bp_tgt->placed_address, &bp_tgt->placed_size);
 
   if (remote_protocol_packets[PACKET_Z1].support == PACKET_DISABLE)
     return -1;
@@ -6251,7 +6105,7 @@ remote_search_memory (struct target_ops* ops,
 
   /* Bail if the pattern is too large.  */
   if (used_pattern_len != pattern_len)
-    error ("pattern is too large to transmit to remote target");
+    error ("Pattern is too large to transmit to remote target.");
 
   if (putpkt_binary (rs->buf, i + escaped_pattern_len) < 0
       || getpkt_sane (&rs->buf, &rs->buf_size, 0) < 0
@@ -6273,12 +6127,12 @@ remote_search_memory (struct target_ops* ops,
     {
       found = 1;
       if (rs->buf[1] != ',')
-       error (_("unknown qSearch:memory reply: %s"), rs->buf);
+       error (_("Unknown qSearch:memory reply: %s"), rs->buf);
       unpack_varlen_hex (rs->buf + 2, &found_addr);
       *found_addrp = found_addr;
     }
   else
-    error (_("unknown qSearch:memory reply: %s"), rs->buf);
+    error (_("Unknown qSearch:memory reply: %s"), rs->buf);
 
   return found;
 }
@@ -6410,7 +6264,7 @@ threadset_test_cmd (char *cmd, int tty)
   int sample_thread = SAMPLE_THREAD;
 
   printf_filtered (_("Remote threadset test\n"));
-  set_thread (sample_thread, 1);
+  set_general_thread (sample_thread);
 }
 
 
@@ -6418,8 +6272,10 @@ static void
 threadalive_test (char *cmd, int tty)
 {
   int sample_thread = SAMPLE_THREAD;
+  int pid = ptid_get_pid (inferior_ptid);
+  ptid_t ptid = ptid_build (pid, 0, sample_thread);
 
-  if (remote_thread_alive (pid_to_ptid (sample_thread)))
+  if (remote_thread_alive (ptid))
     printf_filtered ("PASS: Thread alive test\n");
   else
     printf_filtered ("FAIL: Thread alive test\n");
@@ -6532,10 +6388,21 @@ Fetch and print the remote list of thread identifiers, one pkt only"));
 static char *
 remote_pid_to_str (ptid_t ptid)
 {
-  static char buf[32];
+  static char buf[64];
 
-  xsnprintf (buf, sizeof buf, "Thread %d", ptid_get_pid (ptid));
-  return buf;
+  if (ptid_equal (magic_null_ptid, ptid))
+    {
+      xsnprintf (buf, sizeof buf, "Thread <main>");
+      return buf;
+    }
+  else if (ptid_get_tid (ptid) != 0)
+    {
+      xsnprintf (buf, sizeof buf, "Thread %ld",
+                ptid_get_tid (ptid));
+      return buf;
+    }
+
+  return normal_pid_to_str (ptid);
 }
 
 /* Get the address of the thread local variable in OBJFILE which is
@@ -6552,7 +6419,7 @@ remote_get_thread_local_address (ptid_t ptid, CORE_ADDR lm, CORE_ADDR offset)
 
       strcpy (p, "qGetTLSAddr:");
       p += strlen (p);
-      p += hexnumstr (p, PIDGET (ptid));
+      p += hexnumstr (p, ptid_get_tid (ptid));
       *p++ = ',';
       p += hexnumstr (p, offset);
       *p++ = ',';
@@ -6638,7 +6505,7 @@ static const struct target_desc *
 remote_read_description (struct target_ops *target)
 {
   struct remote_g_packet_data *data
-    = gdbarch_data (current_gdbarch, remote_g_packet_data_handle);
+    = gdbarch_data (target_gdbarch, remote_g_packet_data_handle);
 
   if (!VEC_empty (remote_g_packet_guess_s, data->guesses))
     {
@@ -6802,7 +6669,8 @@ remote_hostio_send_command (int command_bytes, int which_packet,
   int ret, bytes_read;
   char *attachment_tmp;
 
-  if (remote_protocol_packets[which_packet].support == PACKET_DISABLE)
+  if (!remote_desc
+      || remote_protocol_packets[which_packet].support == PACKET_DISABLE)
     {
       *remote_errno = FILEIO_ENOSYS;
       return -1;
@@ -7066,6 +6934,97 @@ remote_hostio_close_cleanup (void *opaque)
   remote_hostio_close (fd, &remote_errno);
 }
 
+
+static void *
+remote_bfd_iovec_open (struct bfd *abfd, void *open_closure)
+{
+  const char *filename = bfd_get_filename (abfd);
+  int fd, remote_errno;
+  int *stream;
+
+  gdb_assert (remote_filename_p (filename));
+
+  fd = remote_hostio_open (filename + 7, FILEIO_O_RDONLY, 0, &remote_errno);
+  if (fd == -1)
+    {
+      errno = remote_fileio_errno_to_host (remote_errno);
+      bfd_set_error (bfd_error_system_call);
+      return NULL;
+    }
+
+  stream = xmalloc (sizeof (int));
+  *stream = fd;
+  return stream;
+}
+
+static int
+remote_bfd_iovec_close (struct bfd *abfd, void *stream)
+{
+  int fd = *(int *)stream;
+  int remote_errno;
+
+  xfree (stream);
+
+  /* Ignore errors on close; these may happen if the remote
+     connection was already torn down.  */
+  remote_hostio_close (fd, &remote_errno);
+
+  return 1;
+}
+
+static file_ptr
+remote_bfd_iovec_pread (struct bfd *abfd, void *stream, void *buf,
+                       file_ptr nbytes, file_ptr offset)
+{
+  int fd = *(int *)stream;
+  int remote_errno;
+  file_ptr pos, bytes;
+
+  pos = 0;
+  while (nbytes > pos)
+    {
+      bytes = remote_hostio_pread (fd, (char *)buf + pos, nbytes - pos,
+                                  offset + pos, &remote_errno);
+      if (bytes == 0)
+        /* Success, but no bytes, means end-of-file.  */
+        break;
+      if (bytes == -1)
+       {
+         errno = remote_fileio_errno_to_host (remote_errno);
+         bfd_set_error (bfd_error_system_call);
+         return -1;
+       }
+
+      pos += bytes;
+    }
+
+  return pos;
+}
+
+static int
+remote_bfd_iovec_stat (struct bfd *abfd, void *stream, struct stat *sb)
+{
+  /* FIXME: We should probably implement remote_hostio_stat.  */
+  sb->st_size = INT_MAX;
+  return 0;
+}
+
+int
+remote_filename_p (const char *filename)
+{
+  return strncmp (filename, "remote:", 7) == 0;
+}
+
+bfd *
+remote_bfd_open (const char *remote_file, const char *target)
+{
+  return bfd_openr_iovec (remote_file, target,
+                         remote_bfd_iovec_open, NULL,
+                         remote_bfd_iovec_pread,
+                         remote_bfd_iovec_close,
+                         remote_bfd_iovec_stat);
+}
+
 void
 remote_file_put (const char *local_file, const char *remote_file, int from_tty)
 {
@@ -7285,12 +7244,6 @@ remote_command (char *args, int from_tty)
   help_list (remote_cmdlist, "remote ", -1, gdb_stdout);
 }
 
-static int
-remote_return_zero (void)
-{
-  return 0;
-}
-
 static void
 init_remote_ops (void)
 {
@@ -7345,8 +7298,12 @@ Specify the serial device it is connected to\n\
   remote_ops.to_flash_done = remote_flash_done;
   remote_ops.to_read_description = remote_read_description;
   remote_ops.to_search_memory = remote_search_memory;
-  remote_ops.to_can_async_p = remote_return_zero;
-  remote_ops.to_is_async_p = remote_return_zero;
+  remote_ops.to_can_async_p = remote_can_async_p;
+  remote_ops.to_is_async_p = remote_is_async_p;
+  remote_ops.to_async = remote_async;
+  remote_ops.to_async_mask = remote_async_mask;
+  remote_ops.to_terminal_inferior = remote_terminal_inferior;
+  remote_ops.to_terminal_ours = remote_terminal_ours;
 }
 
 /* Set up the extended remote vector by making a copy of the standard
@@ -7362,8 +7319,8 @@ init_extended_remote_ops (void)
     "Extended remote serial target in gdb-specific protocol";
   extended_remote_ops.to_doc =
     "Use a remote computer via a serial line, using a gdb-specific protocol.\n\
-Specify the serial device it is connected to (e.g. /dev/ttya).",
-    extended_remote_ops.to_open = extended_remote_open;
+Specify the serial device it is connected to (e.g. /dev/ttya).";
+  extended_remote_ops.to_open = extended_remote_open;
   extended_remote_ops.to_create_inferior = extended_remote_create_inferior;
   extended_remote_ops.to_mourn_inferior = extended_remote_mourn;
   extended_remote_ops.to_detach = extended_remote_detach;
@@ -7373,6 +7330,10 @@ Specify the serial device it is connected to (e.g. /dev/ttya).",
 static int
 remote_can_async_p (void)
 {
+  if (!target_async_permitted)
+    /* We only enable async when the user specifically asks for it.  */
+    return 0;
+
   /* We're async whenever the serial device is.  */
   return remote_async_mask_value && serial_can_async_p (remote_desc);
 }
@@ -7380,6 +7341,10 @@ remote_can_async_p (void)
 static int
 remote_is_async_p (void)
 {
+  if (!target_async_permitted)
+    /* We only enable async when the user specifically asks for it.  */
+    return 0;
+
   /* We're async whenever the serial device is.  */
   return remote_async_mask_value && serial_is_async_p (remote_desc);
 }
@@ -7427,95 +7392,6 @@ remote_async_mask (int new_mask)
   return curr_mask;
 }
 
-/* Target async and target extended-async.
-
-   This are temporary targets, until it is all tested.  Eventually
-   async support will be incorporated int the usual 'remote'
-   target.  */
-
-static void
-init_remote_async_ops (void)
-{
-  remote_async_ops.to_shortname = "async";
-  remote_async_ops.to_longname =
-    "Remote serial target in async version of the gdb-specific protocol";
-  remote_async_ops.to_doc =
-    "Use a remote computer via a serial line, using a gdb-specific protocol.\n\
-Specify the serial device it is connected to (e.g. /dev/ttya).";
-  remote_async_ops.to_open = remote_async_open;
-  remote_async_ops.to_close = remote_close;
-  remote_async_ops.to_detach = remote_detach;
-  remote_async_ops.to_disconnect = remote_disconnect;
-  remote_async_ops.to_resume = remote_async_resume;
-  remote_async_ops.to_wait = remote_async_wait;
-  remote_async_ops.to_fetch_registers = remote_fetch_registers;
-  remote_async_ops.to_store_registers = remote_store_registers;
-  remote_async_ops.to_prepare_to_store = remote_prepare_to_store;
-  remote_async_ops.deprecated_xfer_memory = remote_xfer_memory;
-  remote_async_ops.to_files_info = remote_files_info;
-  remote_async_ops.to_insert_breakpoint = remote_insert_breakpoint;
-  remote_async_ops.to_remove_breakpoint = remote_remove_breakpoint;
-  remote_async_ops.to_can_use_hw_breakpoint = remote_check_watch_resources;
-  remote_async_ops.to_insert_hw_breakpoint = remote_insert_hw_breakpoint;
-  remote_async_ops.to_remove_hw_breakpoint = remote_remove_hw_breakpoint;
-  remote_async_ops.to_insert_watchpoint = remote_insert_watchpoint;
-  remote_async_ops.to_remove_watchpoint = remote_remove_watchpoint;
-  remote_async_ops.to_stopped_by_watchpoint = remote_stopped_by_watchpoint;
-  remote_async_ops.to_stopped_data_address = remote_stopped_data_address;
-  remote_async_ops.to_terminal_inferior = remote_async_terminal_inferior;
-  remote_async_ops.to_terminal_ours = remote_async_terminal_ours;
-  remote_async_ops.to_kill = remote_async_kill;
-  remote_async_ops.to_load = generic_load;
-  remote_async_ops.to_mourn_inferior = remote_async_mourn;
-  remote_async_ops.to_thread_alive = remote_thread_alive;
-  remote_async_ops.to_find_new_threads = remote_threads_info;
-  remote_async_ops.to_pid_to_str = remote_pid_to_str;
-  remote_async_ops.to_extra_thread_info = remote_threads_extra_info;
-  remote_async_ops.to_stop = remote_stop;
-  remote_async_ops.to_xfer_partial = remote_xfer_partial;
-  remote_async_ops.to_rcmd = remote_rcmd;
-  remote_async_ops.to_get_thread_local_address 
-    = remote_get_thread_local_address;
-  remote_async_ops.to_stratum = process_stratum;
-  remote_async_ops.to_has_all_memory = 1;
-  remote_async_ops.to_has_memory = 1;
-  remote_async_ops.to_has_stack = 1;
-  remote_async_ops.to_has_registers = 1;
-  remote_async_ops.to_has_execution = 1;
-  remote_async_ops.to_has_thread_control = tc_schedlock;       /* can lock scheduler */
-  remote_async_ops.to_can_async_p = remote_can_async_p;
-  remote_async_ops.to_is_async_p = remote_is_async_p;
-  remote_async_ops.to_async = remote_async;
-  remote_async_ops.to_async_mask = remote_async_mask;
-  remote_async_ops.to_magic = OPS_MAGIC;
-  remote_async_ops.to_memory_map = remote_memory_map;
-  remote_async_ops.to_flash_erase = remote_flash_erase;
-  remote_async_ops.to_flash_done = remote_flash_done;
-  remote_async_ops.to_read_description = remote_read_description;
-  remote_async_ops.to_search_memory = remote_search_memory;
-}
-
-/* Set up the async extended remote vector by making a copy of the standard
-   remote vector and adding to it.  */
-
-static void
-init_extended_async_remote_ops (void)
-{
-  extended_async_remote_ops = remote_async_ops;
-
-  extended_async_remote_ops.to_shortname = "extended-async";
-  extended_async_remote_ops.to_longname =
-    "Extended remote serial target in async gdb-specific protocol";
-  extended_async_remote_ops.to_doc =
-    "Use a remote computer via a serial line, using an async gdb-specific protocol.\n\
-Specify the serial device it is connected to (e.g. /dev/ttya).",
-    extended_async_remote_ops.to_open = extended_remote_async_open;
-  extended_async_remote_ops.to_create_inferior = extended_remote_async_create_inferior;
-  extended_async_remote_ops.to_mourn_inferior = extended_async_remote_mourn;
-  extended_async_remote_ops.to_detach = extended_remote_detach;
-  extended_async_remote_ops.to_attach = extended_async_remote_attach;
-}
-
 static void
 set_remote_cmd (char *args, int from_tty)
 {
@@ -7590,12 +7466,6 @@ _initialize_remote (void)
   init_extended_remote_ops ();
   add_target (&extended_remote_ops);
 
-  init_remote_async_ops ();
-  add_target (&remote_async_ops);
-
-  init_extended_async_remote_ops ();
-  add_target (&extended_async_remote_ops);
-
   /* Hook into new objfile notification.  */
   observer_attach_new_objfile (remote_new_objfile);
 
@@ -7783,6 +7653,9 @@ Show the maximum size of the address (in bits) in a memory packet."), NULL,
   add_packet_config_cmd (&remote_protocol_packets[PACKET_vRun],
                         "vRun", "run", 0);
 
+  add_packet_config_cmd (&remote_protocol_packets[PACKET_QStartNoAckMode],
+                        "QStartNoAckMode", "noack", 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
@@ -7824,4 +7697,10 @@ Show the remote pathname for \"run\""), NULL, NULL, NULL,
 
   /* Eventually initialize fileio.  See fileio.c */
   initialize_remote_fileio (remote_set_cmdlist, remote_show_cmdlist);
+
+  /* Take advantage of the fact that the LWP field is not used, to tag
+     special ptids with it set to != 0.  */
+  magic_null_ptid = ptid_build (0, 1, -1);
+  not_sent_ptid = ptid_build (0, 1, -2);
+  any_thread_ptid = ptid_build (0, 1, 0);
 }
This page took 0.046962 seconds and 4 git commands to generate.