Tweak handling of remote errors in response to resumption packet
[deliverable/binutils-gdb.git] / gdb / remote.c
index 7ea9cd4cf0618513088ccc522200985018ead2ed..fa940dff7201e2aeac7deb0241e335f310fa05b3 100644 (file)
@@ -1,6 +1,6 @@
 /* Remote target communications for serial-line targets in custom GDB protocol
 
-   Copyright (C) 1988-2019 Free Software Foundation, Inc.
+   Copyright (C) 1988-2020 Free Software Foundation, Inc.
 
    This file is part of GDB.
 
@@ -75,6 +75,7 @@
 #include "gdbsupport/scoped_restore.h"
 #include "gdbsupport/environ.h"
 #include "gdbsupport/byte-vector.h"
+#include <algorithm>
 #include <unordered_map>
 
 /* The remote target.  */
@@ -141,7 +142,7 @@ struct vCont_action_support
   bool S = false;
 };
 
-/* About this many threadisds fit in a packet.  */
+/* About this many threadids fit in a packet.  */
 
 #define MAXTHREADLISTRESULTS 32
 
@@ -1038,12 +1039,7 @@ static struct cmd_list_element *remote_show_cmdlist;
 
 /* Controls whether GDB is willing to use range stepping.  */
 
-static int use_range_stepping = 1;
-
-/* The max number of chars in debug output.  The rest of chars are
-   omitted.  */
-
-#define REMOTE_DEBUG_MAX_CHAR 512
+static bool use_range_stepping = true;
 
 /* Private data that we'll store in (struct thread_info)->priv.  */
 struct remote_thread_info : public private_thread_info
@@ -1272,23 +1268,7 @@ static void
 show_remote_exec_file (struct ui_file *file, int from_tty,
                       struct cmd_list_element *cmd, const char *value)
 {
-  fprintf_filtered (file, "%s\n", remote_exec_file_var);
-}
-
-static int
-compare_pnums (const void *lhs_, const void *rhs_)
-{
-  const struct packet_reg * const *lhs
-    = (const struct packet_reg * const *) lhs_;
-  const struct packet_reg * const *rhs
-    = (const struct packet_reg * const *) rhs_;
-
-  if ((*lhs)->pnum < (*rhs)->pnum)
-    return -1;
-  else if ((*lhs)->pnum == (*rhs)->pnum)
-    return 0;
-  else
-    return 1;
+  fprintf_filtered (file, "%s\n", get_remote_exec_file ());
 }
 
 static int
@@ -1321,8 +1301,9 @@ map_regcache_remote_table (struct gdbarch *gdbarch, struct packet_reg *regs)
     if (regs[regnum].pnum != -1)
       remote_regs[num_remote_regs++] = &regs[regnum];
 
-  qsort (remote_regs, num_remote_regs, sizeof (struct packet_reg *),
-        compare_pnums);
+  std::sort (remote_regs, remote_regs + num_remote_regs,
+            [] (const packet_reg *a, const packet_reg *b)
+             { return a->pnum < b->pnum; });
 
   for (regnum = 0, offset = 0; regnum < num_remote_regs; regnum++)
     {
@@ -1492,12 +1473,12 @@ show_interrupt_sequence (struct ui_file *file, int from_tty,
    to the remote target when gdb connects to it.
    This is mostly needed when you debug the Linux kernel: The Linux kernel
    expects BREAK g which is Magic SysRq g for connecting gdb.  */
-static int interrupt_on_connect = 0;
+static bool interrupt_on_connect = false;
 
 /* This variable is used to implement the "set/show remotebreak" commands.
    Since these commands are now deprecated in favor of "set/show remote
    interrupt-sequence", it no longer has any effect on the code.  */
-static int remote_break;
+static bool remote_break;
 
 static void
 set_remotebreak (const char *args, int from_tty, struct cmd_list_element *c)
@@ -1523,7 +1504,7 @@ show_remotebreak (struct ui_file *file, int from_tty,
    memory packets to ``host::sizeof long'' bytes - (typically 32
    bits).  Consequently, for 64 bit targets, the upper 32 bits of an
    address was never sent.  Since fixing this bug may cause a break in
-   some remote targets this variable is principly provided to
+   some remote targets this variable is principally provided to
    facilitate backward compatibility.  */
 
 static unsigned int remote_address_size;
@@ -1726,6 +1707,23 @@ show_hardware_breakpoint_limit (struct ui_file *file, int from_tty,
                            "breakpoints is %s.\n"), value);
 }
 
+/* Controls the maximum number of characters to display in the debug output
+   for each remote packet.  The remaining characters are omitted.  */
+
+static int remote_packet_max_chars = 512;
+
+/* Show the maximum number of characters to display for each remote packet
+   when remote debugging is enabled.  */
+
+static void
+show_remote_packet_max_chars (struct ui_file *file, int from_tty,
+                             struct cmd_list_element *c,
+                             const char *value)
+{
+  fprintf_filtered (file, _("Number of remote packet characters to "
+                           "display is %s.\n"), value);
+}
+
 long
 remote_target::get_memory_write_packet_size ()
 {
@@ -1864,7 +1862,7 @@ packet_check_result (const char *buf)
       if (buf[0] == 'E'
          && isxdigit (buf[1]) && isxdigit (buf[2])
          && buf[3] == '\0')
-       /* "Enn"  - definitly an error.  */
+       /* "Enn"  - definitely an error.  */
        return PACKET_ERROR;
 
       /* Always treat "E." as an error.  This will be used for
@@ -1970,8 +1968,6 @@ enum {
   PACKET_qXfer_libraries,
   PACKET_qXfer_libraries_svr4,
   PACKET_qXfer_memory_map,
-  PACKET_qXfer_spu_read,
-  PACKET_qXfer_spu_write,
   PACKET_qXfer_osdata,
   PACKET_qXfer_threads,
   PACKET_qXfer_statictrace_read,
@@ -2845,7 +2841,7 @@ remote_target::thread_name (struct thread_info *info)
 
 /* About these extended threadlist and threadinfo packets.  They are
    variable length packets but, the fields within them are often fixed
-   length.  They are redundent enough to send over UDP as is the
+   length.  They are redundant enough to send over UDP as is the
    remote protocol in general.  There is a matching unit test module
    in libstub.  */
 
@@ -3252,7 +3248,7 @@ remote_target::remote_unpack_thread_info_response (char *pkt,
     }
   copy_threadref (&info->threadid, &ref);
 
-  /* Loop on tagged fields , try to bail if somthing goes wrong.  */
+  /* Loop on tagged fields , try to bail if something goes wrong.  */
 
   /* Packets are terminated with nulls.  */
   while ((pkt < limit) && mask && *pkt)
@@ -3391,7 +3387,7 @@ remote_target::remote_get_threadlist (int startflag, threadref *nextthread,
   struct remote_state *rs = get_remote_state ();
   int result = 1;
 
-  /* Trancate result limit to be smaller than the packet size.  */
+  /* Truncate result limit to be smaller than the packet size.  */
   if ((((result_limit + 1) * BUF_THREAD_ID_SIZE) + 10)
       >= get_remote_packet_size ())
     result_limit = (get_remote_packet_size () / BUF_THREAD_ID_SIZE) - 2;
@@ -3413,8 +3409,8 @@ remote_target::remote_get_threadlist (int startflag, threadref *nextthread,
   if (!threadmatch (&rs->echo_nextthread, nextthread))
     {
       /* FIXME: This is a good reason to drop the packet.  */
-      /* Possably, there is a duplicate response.  */
-      /* Possabilities :
+      /* Possibly, there is a duplicate response.  */
+      /* Possibilities :
          retransmit immediatly - race conditions
          retransmit after timeout - yes
          exit
@@ -4053,7 +4049,6 @@ remote_target::get_offsets ()
   char *ptr;
   int lose, num_segments = 0, do_sections, do_segments;
   CORE_ADDR text_addr, data_addr, bss_addr, segments[2];
-  struct section_offsets *offs;
   struct symfile_segment_data *data;
 
   if (symfile_objfile == NULL)
@@ -4132,10 +4127,7 @@ remote_target::get_offsets ()
   else if (*ptr != '\0')
     warning (_("Target reported unsupported offsets: %s"), buf);
 
-  offs = ((struct section_offsets *)
-         alloca (SIZEOF_N_SECTION_OFFSETS (symfile_objfile->num_sections)));
-  memcpy (offs, symfile_objfile->section_offsets,
-         SIZEOF_N_SECTION_OFFSETS (symfile_objfile->num_sections));
+  section_offsets offs = symfile_objfile->section_offsets;
 
   data = get_symfile_segment_data (symfile_objfile->obfd);
   do_segments = (data != NULL);
@@ -4188,15 +4180,15 @@ remote_target::get_offsets ()
 
   if (do_sections)
     {
-      offs->offsets[SECT_OFF_TEXT (symfile_objfile)] = text_addr;
+      offs[SECT_OFF_TEXT (symfile_objfile)] = text_addr;
 
       /* This is a temporary kludge to force data and bss to use the
         same offsets because that's what nlmconv does now.  The real
         solution requires changes to the stub and remote.c that I
         don't have time to do right now.  */
 
-      offs->offsets[SECT_OFF_DATA (symfile_objfile)] = data_addr;
-      offs->offsets[SECT_OFF_BSS (symfile_objfile)] = data_addr;
+      offs[SECT_OFF_DATA (symfile_objfile)] = data_addr;
+      offs[SECT_OFF_BSS (symfile_objfile)] = data_addr;
     }
 
   objfile_relocate (symfile_objfile, offs);
@@ -5060,7 +5052,7 @@ remote_target::remote_packet_size (const protocol_feature *feature,
   rs->explicit_packet_size = packet_size;
 }
 
-void
+static void
 remote_packet_size (remote_target *remote, const protocol_feature *feature,
                    enum packet_support support, const char *value)
 {
@@ -5083,10 +5075,6 @@ static const struct protocol_feature remote_protocol_features[] = {
     remote_supported_packet, PACKET_augmented_libraries_svr4_read_feature },
   { "qXfer:memory-map:read", PACKET_DISABLE, remote_supported_packet,
     PACKET_qXfer_memory_map },
-  { "qXfer:spu:read", PACKET_DISABLE, remote_supported_packet,
-    PACKET_qXfer_spu_read },
-  { "qXfer:spu:write", PACKET_DISABLE, remote_supported_packet,
-    PACKET_qXfer_spu_write },
   { "qXfer:osdata:read", PACKET_DISABLE, remote_supported_packet,
     PACKET_qXfer_osdata },
   { "qXfer:threads:read", PACKET_DISABLE, remote_supported_packet,
@@ -5189,7 +5177,8 @@ register_remote_support_xml (const char *xml)
   else
     {
       char *copy = xstrdup (remote_support_xml + 13);
-      char *p = strtok (copy, ",");
+      char *saveptr;
+      char *p = strtok_r (copy, ",", &saveptr);
 
       do
        {
@@ -5200,7 +5189,7 @@ register_remote_support_xml (const char *xml)
              return;
            }
        }
-      while ((p = strtok (NULL, ",")) != NULL);
+      while ((p = strtok_r (NULL, ",", &saveptr)) != NULL);
       xfree (copy);
 
       remote_support_xml = reconcat (remote_support_xml,
@@ -5799,7 +5788,7 @@ extended_remote_target::attach (const char *args, int from_tty)
 
   if (from_tty)
     {
-      char *exec_file = get_exec_file (0);
+      const char *exec_file = get_exec_file (0);
 
       if (exec_file)
        printf_unfiltered (_("Attaching to program: %s, %s\n"), exec_file,
@@ -6833,7 +6822,7 @@ remote_target::stop_reply_queue_length ()
   return rs->stop_reply_queue.size ();
 }
 
-void
+static void
 remote_notif_stop_parse (remote_target *remote,
                         struct notif_client *self, const char *buf,
                         struct notif_event *event)
@@ -7542,7 +7531,7 @@ Packet: '%s'\n"),
       <GDB marks the REMOTE_ASYNC_GET_PENDING_EVENTS_TOKEN>
     2.5) <-- (registers reply to step #2.3)
 
-   Eventualy after step #2.5, we return to the event loop, which
+   Eventually after step #2.5, we return to the event loop, which
    notices there's an event on the
    REMOTE_ASYNC_GET_PENDING_EVENTS_TOKEN event and calls the
    associated callback --- the function below.  At this point, we're
@@ -7703,6 +7692,17 @@ remote_target::wait_ns (ptid_t ptid, struct target_waitstatus *status, int optio
     }
 }
 
+/* Return the first resumed thread.  */
+
+static ptid_t
+first_remote_resumed_thread ()
+{
+  for (thread_info *tp : all_non_exited_threads (minus_one_ptid))
+    if (tp->resumed)
+      return tp->ptid;
+  return null_ptid;
+}
+
 /* Wait until the remote machine stops, then return, storing status in
    STATUS just as `wait' would.  */
 
@@ -7839,7 +7839,7 @@ remote_target::wait_as (ptid_t ptid, target_waitstatus *status, int options)
       if (event_ptid != null_ptid)
        record_currthread (rs, event_ptid);
       else
-       event_ptid = inferior_ptid;
+       event_ptid = first_remote_resumed_thread ();
     }
   else
     /* A process exit.  Invalidate our notion of current thread.  */
@@ -8749,9 +8749,7 @@ remote_target::remote_xfer_live_readonly_partial (gdb_byte *readbuf,
 
   secp = target_section_by_addr (this, memaddr);
   if (secp != NULL
-      && (bfd_get_section_flags (secp->the_bfd_section->owner,
-                                secp->the_bfd_section)
-         & SEC_READONLY))
+      && (bfd_section_flags (secp->the_bfd_section) & SEC_READONLY))
     {
       struct target_section *p;
       ULONGEST memend = memaddr + len;
@@ -9140,15 +9138,21 @@ remote_target::putpkt_binary (const char *buf, int cnt)
          *p = '\0';
 
          int len = (int) (p - buf2);
+         int max_chars;
+
+         if (remote_packet_max_chars < 0)
+           max_chars = len;
+         else
+           max_chars = remote_packet_max_chars;
 
          std::string str
-           = escape_buffer (buf2, std::min (len, REMOTE_DEBUG_MAX_CHAR));
+           = escape_buffer (buf2, std::min (len, max_chars));
 
          fprintf_unfiltered (gdb_stdlog, "Sending packet: %s", str.c_str ());
 
-         if (len > REMOTE_DEBUG_MAX_CHAR)
+         if (len > max_chars)
            fprintf_unfiltered (gdb_stdlog, "[%d bytes omitted]",
-                               len - REMOTE_DEBUG_MAX_CHAR);
+                               len - max_chars);
 
          fprintf_unfiltered (gdb_stdlog, "...");
 
@@ -9584,16 +9588,23 @@ remote_target::getpkt_or_notif_sane_1 (gdb::char_vector *buf,
        {
          if (remote_debug)
            {
+             int max_chars;
+
+             if (remote_packet_max_chars < 0)
+               max_chars = val;
+             else
+               max_chars = remote_packet_max_chars;
+
              std::string str
                = escape_buffer (buf->data (),
-                                std::min (val, REMOTE_DEBUG_MAX_CHAR));
+                                std::min (val, max_chars));
 
              fprintf_unfiltered (gdb_stdlog, "Packet received: %s",
                                  str.c_str ());
 
-             if (val > REMOTE_DEBUG_MAX_CHAR)
+             if (val > max_chars)
                fprintf_unfiltered (gdb_stdlog, "[%d bytes omitted]",
-                                   val - REMOTE_DEBUG_MAX_CHAR);
+                                   val - max_chars);
 
              fprintf_unfiltered (gdb_stdlog, "\n");
            }
@@ -9843,26 +9854,6 @@ remote_target::mourn_inferior ()
 
   /* Call common code to mark the inferior as not running.  */
   generic_mourn_inferior ();
-
-  if (!have_inferiors ())
-    {
-      if (!remote_multi_process_p (rs))
-       {
-         /* Check whether the target is running now - some remote stubs
-            automatically restart after kill.  */
-         putpkt ("?");
-         getpkt (&rs->buf, 0);
-
-         if (rs->buf[0] == 'S' || rs->buf[0] == 'T')
-           {
-             /* 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 = magic_null_ptid;
-           }
-       }
-    }
 }
 
 bool
@@ -10656,11 +10647,11 @@ compare_sections_command (const char *args, int from_tty)
       if (read_only && (s->flags & SEC_READONLY) == 0)
        continue;               /* Skip writeable sections */
 
-      size = bfd_get_section_size (s);
+      size = bfd_section_size (s);
       if (size == 0)
        continue;               /* Skip zero-length section.  */
 
-      sectname = bfd_get_section_name (exec_bfd, s);
+      sectname = bfd_section_name (s);
       if (args && strcmp (args, sectname) != 0)
        continue;               /* Not the section selected by user.  */
 
@@ -10860,19 +10851,6 @@ remote_target::xfer_partial (enum target_object object,
                                  xfered_len);
     }
 
-  /* Handle SPU memory using qxfer packets.  */
-  if (object == TARGET_OBJECT_SPU)
-    {
-      if (readbuf)
-       return remote_read_qxfer ("spu", annex, readbuf, offset, len,
-                                 xfered_len, &remote_protocol_packets
-                                 [PACKET_qXfer_spu_read]);
-      else
-       return remote_write_qxfer ("spu", annex, writebuf, offset, len,
-                                  xfered_len, &remote_protocol_packets
-                                  [PACKET_qXfer_spu_write]);
-    }
-
   /* Handle extra signal info using qxfer packets.  */
   if (object == TARGET_OBJECT_SIGNAL_INFO)
     {
@@ -11304,7 +11282,7 @@ output_threadid (char *title, threadref *ref)
 {
   char hexid[20];
 
-  pack_threadid (&hexid[0], ref);      /* Convert threead id into hex.  */
+  pack_threadid (&hexid[0], ref);      /* Convert thread id into hex.  */
   hexid[16] = 0;
   printf_filtered ("%s  %s\n", title, (&hexid[0]));
 }
@@ -13059,7 +13037,6 @@ void
 remote_target::trace_set_readonly_regions ()
 {
   asection *s;
-  bfd *abfd = NULL;
   bfd_size_type size;
   bfd_vma vma;
   int anysecs = 0;
@@ -13083,8 +13060,8 @@ remote_target::trace_set_readonly_regions ()
        continue;
 
       anysecs = 1;
-      vma = bfd_get_section_vma (abfd, s);
-      size = bfd_get_section_size (s);
+      vma = bfd_section_vma (s);
+      size = bfd_section_size (s);
       sprintf_vma (tmp1, vma);
       sprintf_vma (tmp2, vma + size);
       sec_length = 1 + strlen (tmp1) + 1 + strlen (tmp2);
@@ -13124,14 +13101,13 @@ remote_target::get_trace_status (struct trace_status *ts)
 {
   /* Initialize it just to avoid a GCC false warning.  */
   char *p = NULL;
-  /* FIXME we need to get register block size some other way.  */
-  extern int trace_regblock_size;
   enum packet_result result;
   struct remote_state *rs = get_remote_state ();
 
   if (packet_support (PACKET_qTStatus) == PACKET_DISABLE)
     return -1;
 
+  /* FIXME we need to get register block size some other way.  */
   trace_regblock_size
     = rs->get_remote_arch_state (target_gdbarch ())->sizeof_g_packet;
 
@@ -13700,6 +13676,11 @@ remote_target::remote_btrace_maybe_reopen ()
   int warned = 0;
 #endif
 
+  /* Don't bother walking the entirety of the remote thread list when
+     we know the feature isn't supported by the remote.  */
+  if (packet_support (PACKET_qXfer_btrace_conf) != PACKET_ENABLE)
+    return;
+
   scoped_restore_current_thread restore_thread;
 
   for (thread_info *tp : all_non_exited_threads ())
@@ -14479,12 +14460,6 @@ Show the maximum size of the address (in bits) in a memory packet."), NULL,
   add_packet_config_cmd (&remote_protocol_packets[PACKET_qXfer_memory_map],
                         "qXfer:memory-map:read", "memory-map", 0);
 
-  add_packet_config_cmd (&remote_protocol_packets[PACKET_qXfer_spu_read],
-                         "qXfer:spu:read", "read-spu-object", 0);
-
-  add_packet_config_cmd (&remote_protocol_packets[PACKET_qXfer_spu_write],
-                         "qXfer:spu:write", "write-spu-object", 0);
-
   add_packet_config_cmd (&remote_protocol_packets[PACKET_qXfer_osdata],
                         "qXfer:osdata:read", "osdata", 0);
 
@@ -14760,6 +14735,14 @@ of time passes without a response from the target, an error occurs."),
                            show_watchdog,
                            &setlist, &showlist);
 
+  add_setshow_zuinteger_unlimited_cmd ("remote-packet-max-chars", no_class,
+                                      &remote_packet_max_chars, _("\
+Set the maximum number of characters to display for each remote packet."), _("\
+Show the maximum number of characters to display for each remote packet."), _("\
+Specify \"unlimited\" to display all the characters."),
+                                      NULL, show_remote_packet_max_chars,
+                                      &setdebuglist, &showdebuglist);
+
   /* Eventually initialize fileio.  See fileio.c */
   initialize_remote_fileio (remote_set_cmdlist, remote_show_cmdlist);
 }
This page took 0.05287 seconds and 4 git commands to generate.