2007-06-13 Markus Deuling <deuling@de.ibm.com>
[deliverable/binutils-gdb.git] / gdb / remote.c
index 866c477b748f48b3fac2f53a09f785857e2ac101..e7a7d35caa4f95b0b9fc4b96d364adddd4164691 100644 (file)
@@ -89,9 +89,9 @@ static void build_remote_gdbarch_data (void);
 
 static void remote_files_info (struct target_ops *ignore);
 
-static void remote_prepare_to_store (void);
+static void remote_prepare_to_store (struct regcache *regcache);
 
-static void remote_fetch_registers (int regno);
+static void remote_fetch_registers (struct regcache *regcache, int regno);
 
 static void remote_resume (ptid_t ptid, int step,
                            enum target_signal siggnal);
@@ -108,7 +108,7 @@ static void remote_open_1 (char *, int, struct target_ops *, int extended_p,
 
 static void remote_close (int quitting);
 
-static void remote_store_registers (int regno);
+static void remote_store_registers (struct regcache *regcache, int regno);
 
 static void remote_mourn (void);
 static void remote_async_mourn (void);
@@ -260,7 +260,8 @@ struct packet_reg
   int in_g_packet; /* Always part of G packet.  */
   /* long size in bytes;  == register_size (current_gdbarch, regnum);
      at present.  */
-  /* char *name; == REGISTER_NAME (regnum); at present.  */
+  /* char *name; == gdbarch_register_name (current_gdbarch, regnum);
+     at present.  */
 };
 
 struct remote_arch_state
@@ -269,7 +270,7 @@ struct remote_arch_state
   long sizeof_g_packet;
 
   /* Description of the remote protocol registers indexed by REGNUM
-     (making an array NUM_REGS in size).  */
+     (making an array gdbarch_num_regs in size).  */
   struct packet_reg *regs;
 
   /* This is the size (in chars) of the first response to the ``g''
@@ -336,8 +337,10 @@ init_remote_state (struct gdbarch *gdbarch)
 
   /* Use the architecture to build a regnum<->pnum table, which will be
      1:1 unless a feature set specifies otherwise.  */
-  rsa->regs = GDBARCH_OBSTACK_CALLOC (gdbarch, NUM_REGS, struct packet_reg);
-  for (regnum = 0; regnum < NUM_REGS; regnum++)
+  rsa->regs = GDBARCH_OBSTACK_CALLOC (gdbarch,
+                                     gdbarch_num_regs (current_gdbarch),
+                                     struct packet_reg);
+  for (regnum = 0; regnum < gdbarch_num_regs (current_gdbarch); regnum++)
     {
       struct packet_reg *r = &rsa->regs[regnum];
 
@@ -354,8 +357,11 @@ init_remote_state (struct gdbarch *gdbarch)
      with a remote protocol number, in order of ascending protocol
      number.  */
 
-  remote_regs = alloca (NUM_REGS * sizeof (struct packet_reg *));
-  for (num_remote_regs = 0, regnum = 0; regnum < NUM_REGS; regnum++)
+  remote_regs = alloca (gdbarch_num_regs (current_gdbarch) 
+                       * sizeof (struct packet_reg *));
+  for (num_remote_regs = 0, regnum = 0;
+       regnum < gdbarch_num_regs (current_gdbarch);
+       regnum++)
     if (rsa->regs[regnum].pnum != -1)
       remote_regs[num_remote_regs++] = &rsa->regs[regnum];
 
@@ -423,7 +429,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 >= NUM_REGS)
+  if (regnum < 0 && regnum >= gdbarch_num_regs (current_gdbarch))
     return NULL;
   else
     {
@@ -437,7 +443,7 @@ static struct packet_reg *
 packet_reg_from_pnum (struct remote_arch_state *rsa, LONGEST pnum)
 {
   int i;
-  for (i = 0; i < NUM_REGS; i++)
+  for (i = 0; i < gdbarch_num_regs (current_gdbarch); i++)
     {
       struct packet_reg *r = &rsa->regs[i];
       if (r->pnum == pnum)
@@ -902,6 +908,8 @@ enum {
   PACKET_qXfer_auxv,
   PACKET_qXfer_features,
   PACKET_qXfer_memory_map,
+  PACKET_qXfer_spu_read,
+  PACKET_qXfer_spu_write,
   PACKET_qGetTLSAddr,
   PACKET_qSupported,
   PACKET_QPassSignals,
@@ -2306,6 +2314,10 @@ static struct protocol_feature remote_protocol_features[] = {
     PACKET_qXfer_features },
   { "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 },
   { "QPassSignals", PACKET_DISABLE, remote_supported_packet,
     PACKET_QPassSignals },
 };
@@ -2600,7 +2612,11 @@ remote_detach (char *args, int from_tty)
 
   /* Tell the remote target to detach.  */
   strcpy (rs->buf, "D");
-  remote_send (&rs->buf, &rs->buf_size);
+  putpkt (rs->buf);
+  getpkt (&rs->buf, &rs->buf_size, 0);
+
+  if (rs->buf[0] == 'E')
+    error (_("Can't detach process."));
 
   /* Unregister the file descriptor from the event loop.  */
   if (target_is_async_p ())
@@ -3486,7 +3502,7 @@ got_status:
 /* Fetch a single register using a 'p' packet.  */
 
 static int
-fetch_register_using_p (struct packet_reg *reg)
+fetch_register_using_p (struct regcache *regcache, struct packet_reg *reg)
 {
   struct remote_state *rs = get_remote_state ();
   char *buf, *p;
@@ -3521,8 +3537,7 @@ fetch_register_using_p (struct packet_reg *reg)
   /* If this register is unfetchable, tell the regcache.  */
   if (buf[0] == 'x')
     {
-      regcache_raw_supply (current_regcache, reg->regnum, NULL);
-      set_register_cached (reg->regnum, -1);
+      regcache_raw_supply (regcache, reg->regnum, NULL);
       return 1;
     }
 
@@ -3537,7 +3552,7 @@ fetch_register_using_p (struct packet_reg *reg)
       regp[i++] = fromhex (p[0]) * 16 + fromhex (p[1]);
       p += 2;
     }
-  regcache_raw_supply (current_regcache, reg->regnum, regp);
+  regcache_raw_supply (regcache, reg->regnum, regp);
   return 1;
 }
 
@@ -3578,7 +3593,7 @@ send_g_packet (void)
 }
 
 static void
-process_g_packet (void)
+process_g_packet (struct regcache *regcache)
 {
   struct remote_state *rs = get_remote_state ();
   struct remote_arch_state *rsa = get_remote_arch_state ();
@@ -3589,8 +3604,6 @@ process_g_packet (void)
   buf_len = strlen (rs->buf);
 
   /* Further sanity checks, with knowledge of the architecture.  */
-  if (REGISTER_BYTES_OK_P () && !REGISTER_BYTES_OK (buf_len / 2))
-    error (_("Remote 'g' packet reply is wrong length: %s"), rs->buf);
   if (buf_len > 2 * rsa->sizeof_g_packet)
     error (_("Remote 'g' packet reply is too long: %s"), rs->buf);
 
@@ -3608,7 +3621,7 @@ process_g_packet (void)
     {
       rsa->sizeof_g_packet = buf_len / 2;
 
-      for (i = 0; i < NUM_REGS; i++)
+      for (i = 0; i < gdbarch_num_regs (current_gdbarch); i++)
        {
          if (rsa->regs[i].pnum == -1)
            continue;
@@ -3646,7 +3659,7 @@ process_g_packet (void)
 
   {
     int i;
-    for (i = 0; i < NUM_REGS; i++)
+    for (i = 0; i < gdbarch_num_regs (current_gdbarch); i++)
       {
        struct packet_reg *r = &rsa->regs[i];
        if (r->in_g_packet)
@@ -3660,11 +3673,10 @@ process_g_packet (void)
                gdb_assert (r->offset * 2 < strlen (rs->buf));
                /* The register isn't available, mark it as such (at
                    the same time setting the value to zero).  */
-               regcache_raw_supply (current_regcache, r->regnum, NULL);
-               set_register_cached (i, -1);
+               regcache_raw_supply (regcache, r->regnum, NULL);
              }
            else
-             regcache_raw_supply (current_regcache, r->regnum,
+             regcache_raw_supply (regcache, r->regnum,
                                   regs + r->offset);
          }
       }
@@ -3672,14 +3684,14 @@ process_g_packet (void)
 }
 
 static void
-fetch_registers_using_g (void)
+fetch_registers_using_g (struct regcache *regcache)
 {
   send_g_packet ();
-  process_g_packet ();
+  process_g_packet (regcache);
 }
 
 static void
-remote_fetch_registers (int regnum)
+remote_fetch_registers (struct regcache *regcache, int regnum)
 {
   struct remote_state *rs = get_remote_state ();
   struct remote_arch_state *rsa = get_remote_arch_state ();
@@ -3698,30 +3710,28 @@ remote_fetch_registers (int regnum)
         contents, so fall back to 'p'.  */
       if (reg->in_g_packet)
        {
-         fetch_registers_using_g ();
+         fetch_registers_using_g (regcache);
          if (reg->in_g_packet)
            return;
        }
 
-      if (fetch_register_using_p (reg))
+      if (fetch_register_using_p (regcache, reg))
        return;
 
       /* This register is not available.  */
-      regcache_raw_supply (current_regcache, reg->regnum, NULL);
-      set_register_cached (reg->regnum, -1);
+      regcache_raw_supply (regcache, reg->regnum, NULL);
 
       return;
     }
 
-  fetch_registers_using_g ();
+  fetch_registers_using_g (regcache);
 
-  for (i = 0; i < NUM_REGS; i++)
+  for (i = 0; i < gdbarch_num_regs (current_gdbarch); i++)
     if (!rsa->regs[i].in_g_packet)
-      if (!fetch_register_using_p (&rsa->regs[i]))
+      if (!fetch_register_using_p (regcache, &rsa->regs[i]))
        {
          /* This register is not available.  */
-         regcache_raw_supply (current_regcache, i, NULL);
-         set_register_cached (i, -1);
+         regcache_raw_supply (regcache, i, NULL);
        }
 }
 
@@ -3730,7 +3740,7 @@ remote_fetch_registers (int regnum)
    first.  */
 
 static void
-remote_prepare_to_store (void)
+remote_prepare_to_store (struct regcache *regcache)
 {
   struct remote_arch_state *rsa = get_remote_arch_state ();
   int i;
@@ -3742,9 +3752,9 @@ remote_prepare_to_store (void)
     case PACKET_DISABLE:
     case PACKET_SUPPORT_UNKNOWN:
       /* Make sure all the necessary registers are cached.  */
-      for (i = 0; i < NUM_REGS; i++)
+      for (i = 0; i < gdbarch_num_regs (current_gdbarch); i++)
        if (rsa->regs[i].in_g_packet)
-         regcache_raw_read (current_regcache, rsa->regs[i].regnum, buf);
+         regcache_raw_read (regcache, rsa->regs[i].regnum, buf);
       break;
     case PACKET_ENABLE:
       break;
@@ -3755,7 +3765,7 @@ remote_prepare_to_store (void)
    packet was not recognized.  */
 
 static int
-store_register_using_P (struct packet_reg *reg)
+store_register_using_P (const struct regcache *regcache, struct packet_reg *reg)
 {
   struct remote_state *rs = get_remote_state ();
   struct remote_arch_state *rsa = get_remote_arch_state ();
@@ -3772,7 +3782,7 @@ store_register_using_P (struct packet_reg *reg)
 
   xsnprintf (buf, get_remote_packet_size (), "P%s=", phex_nz (reg->pnum, 0));
   p = buf + strlen (buf);
-  regcache_raw_collect (current_regcache, reg->regnum, regp);
+  regcache_raw_collect (regcache, reg->regnum, regp);
   bin2hex (regp, p, register_size (current_gdbarch, reg->regnum));
   remote_send (&rs->buf, &rs->buf_size);
 
@@ -3794,7 +3804,7 @@ store_register_using_P (struct packet_reg *reg)
    contents of the register cache buffer.  FIXME: ignores errors.  */
 
 static void
-store_registers_using_G (void)
+store_registers_using_G (const struct regcache *regcache)
 {
   struct remote_state *rs = get_remote_state ();
   struct remote_arch_state *rsa = get_remote_arch_state ();
@@ -3807,11 +3817,11 @@ store_registers_using_G (void)
     int i;
     regs = alloca (rsa->sizeof_g_packet);
     memset (regs, 0, rsa->sizeof_g_packet);
-    for (i = 0; i < NUM_REGS; i++)
+    for (i = 0; i < gdbarch_num_regs (current_gdbarch); i++)
       {
        struct packet_reg *r = &rsa->regs[i];
        if (r->in_g_packet)
-         regcache_raw_collect (current_regcache, r->regnum, regs + r->offset);
+         regcache_raw_collect (regcache, r->regnum, regs + r->offset);
       }
   }
 
@@ -3829,7 +3839,7 @@ store_registers_using_G (void)
    of the register cache buffer.  FIXME: ignores errors.  */
 
 static void
-remote_store_registers (int regnum)
+remote_store_registers (struct regcache *regcache, int regnum)
 {
   struct remote_state *rs = get_remote_state ();
   struct remote_arch_state *rsa = get_remote_arch_state ();
@@ -3846,7 +3856,7 @@ remote_store_registers (int regnum)
         possible; we often change only a small number of registers.
         Sometimes we change a larger number; we'd need help from a
         higher layer to know to use 'G'.  */
-      if (store_register_using_P (reg))
+      if (store_register_using_P (regcache, reg))
        return;
 
       /* For now, don't complain if we have no way to write the
@@ -3856,15 +3866,15 @@ remote_store_registers (int regnum)
       if (!reg->in_g_packet)
        return;
 
-      store_registers_using_G ();
+      store_registers_using_G (regcache);
       return;
     }
 
-  store_registers_using_G ();
+  store_registers_using_G (regcache);
 
-  for (i = 0; i < NUM_REGS; i++)
+  for (i = 0; i < gdbarch_num_regs (current_gdbarch); i++)
     if (!rsa->regs[i].in_g_packet)
-      if (!store_register_using_P (&rsa->regs[i]))
+      if (!store_register_using_P (regcache, &rsa->regs[i]))
        /* See above for why we do not issue an error here.  */
        continue;
 }
@@ -4108,12 +4118,6 @@ remote_write_bytes_aux (const char *header, CORE_ADDR memaddr,
     internal_error (__FILE__, __LINE__,
                    "remote_write_bytes_aux: bad packet format");
 
-  /* Should this be the selected frame?  */
-  gdbarch_remote_translate_xfer_address (current_gdbarch,
-                                        current_regcache,
-                                        memaddr, len,
-                                        &memaddr, &len);
-
   if (len <= 0)
     return 0;
 
@@ -4306,12 +4310,6 @@ remote_read_bytes (CORE_ADDR memaddr, gdb_byte *myaddr, int len)
   int max_buf_size;            /* Max size of packet output buffer.  */
   int origlen;
 
-  /* Should this be the selected frame?  */
-  gdbarch_remote_translate_xfer_address (current_gdbarch,
-                                        current_regcache,
-                                        memaddr, len,
-                                        &memaddr, &len);
-
   if (len <= 0)
     return 0;
 
@@ -5130,7 +5128,8 @@ remote_insert_breakpoint (struct bp_target_info *bp_tgt)
       *(p++) = 'Z';
       *(p++) = '0';
       *(p++) = ',';
-      BREAKPOINT_FROM_PC (&bp_tgt->placed_address, &bp_tgt->placed_size);
+      gdbarch_breakpoint_from_pc
+       (current_gdbarch, &bp_tgt->placed_address, &bp_tgt->placed_size);
       addr = (ULONGEST) remote_address_masked (bp_tgt->placed_address);
       p += hexnumstr (p, addr);
       sprintf (p, ",%d", bp_tgt->placed_size);
@@ -5325,7 +5324,8 @@ remote_insert_hw_breakpoint (struct bp_target_info *bp_tgt)
   /* The length field should be set to the size of a breakpoint
      instruction, even though we aren't inserting one ourselves.  */
 
-  BREAKPOINT_FROM_PC (&bp_tgt->placed_address, &bp_tgt->placed_size);
+  gdbarch_breakpoint_from_pc
+    (current_gdbarch, &bp_tgt->placed_address, &bp_tgt->placed_size);
 
   if (remote_protocol_packets[PACKET_Z1].support == PACKET_DISABLE)
     return -1;
@@ -5524,6 +5524,45 @@ the loaded file\n"));
     printf_filtered (_("No loaded section named '%s'.\n"), args);
 }
 
+/* Write LEN bytes from WRITEBUF into OBJECT_NAME/ANNEX at OFFSET
+   into remote target.  The number of bytes written to the remote
+   target is returned, or -1 for error.  */
+
+static LONGEST
+remote_write_qxfer (struct target_ops *ops, const char *object_name,
+                    const char *annex, const gdb_byte *writebuf, 
+                    ULONGEST offset, LONGEST len, 
+                    struct packet_config *packet)
+{
+  int i, buf_len;
+  ULONGEST n;
+  gdb_byte *wbuf;
+  struct remote_state *rs = get_remote_state ();
+  int max_size = get_memory_write_packet_size (); 
+
+  if (packet->support == PACKET_DISABLE)
+    return -1;
+
+  /* Insert header.  */
+  i = snprintf (rs->buf, max_size, 
+               "qXfer:%s:write:%s:%s:",
+               object_name, annex ? annex : "",
+               phex_nz (offset, sizeof offset));
+  max_size -= (i + 1);
+
+  /* Escape as much data as fits into rs->buf.  */
+  buf_len = remote_escape_output 
+    (writebuf, len, (rs->buf + i), &max_size, max_size);
+
+  if (putpkt_binary (rs->buf, i + buf_len) < 0
+      || getpkt_sane (&rs->buf, &rs->buf_size, 0) < 0
+      || packet_ok (rs->buf, packet) != PACKET_OK)
+    return -1;
+
+  unpack_varlen_hex (rs->buf, &n);
+  return n;
+}
+
 /* Read OBJECT_NAME/ANNEX from the remote target using a qXfer packet.
    Data at OFFSET, of up to LEN bytes, is read into READBUF; the
    number of bytes read is returned, or 0 for EOF, or -1 for error.
@@ -5596,9 +5635,9 @@ remote_read_qxfer (struct target_ops *ops, const char *object_name,
   i = remote_unescape_input (rs->buf + 1, packet_len - 1, readbuf, n);
 
   /* 'l' is an EOF marker, possibly including a final block of data,
-     or possibly empty.  Record it to bypass the next read, if one is
-     issued.  */
-  if (rs->buf[0] == 'l')
+     or possibly empty.  If we have the final block of a non-empty
+     object, record this fact to bypass a subsequent partial read.  */
+  if (rs->buf[0] == 'l' && offset + i > 0)
     {
       finished_object = xstrdup (object_name);
       finished_annex = xstrdup (annex ? annex : "");
@@ -5637,6 +5676,19 @@ remote_xfer_partial (struct target_ops *ops, enum target_object object,
        return -1;
     }
 
+  /* Handle SPU memory using qxfer packets. */
+  if (object == TARGET_OBJECT_SPU)
+    {
+      if (readbuf)
+       return remote_read_qxfer (ops, "spu", annex, readbuf, offset, len,
+                                 &remote_protocol_packets
+                                   [PACKET_qXfer_spu_read]);
+      else
+       return remote_write_qxfer (ops, "spu", annex, writebuf, offset, len,
+                                  &remote_protocol_packets
+                                    [PACKET_qXfer_spu_write]);
+    }
+
   /* Only handle flash writes.  */
   if (writebuf != NULL)
     {
@@ -6362,20 +6414,12 @@ build_remote_gdbarch_data (void)
   remote_address_size = TARGET_ADDR_BIT;
 }
 
-/* Saved pointer to previous owner of the new_objfile event.  */
-static void (*remote_new_objfile_chain) (struct objfile *);
-
 /* Function to be called whenever a new objfile (shlib) is detected.  */
 static void
 remote_new_objfile (struct objfile *objfile)
 {
   if (remote_desc != 0)                /* Have a remote connection.  */
-    {
-      remote_check_symbols (objfile);
-    }
-  /* Call predecessor on chain, if any.  */
-  if (remote_new_objfile_chain)
-    remote_new_objfile_chain (objfile);
+    remote_check_symbols (objfile);
 }
 
 void
@@ -6415,8 +6459,7 @@ _initialize_remote (void)
   add_target (&extended_async_remote_ops);
 
   /* Hook into new objfile notification.  */
-  remote_new_objfile_chain = deprecated_target_new_objfile_hook;
-  deprecated_target_new_objfile_hook  = remote_new_objfile;
+  observer_attach_new_objfile (remote_new_objfile);
 
 #if 0
   init_remote_threadtests ();
@@ -6556,6 +6599,12 @@ 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_qGetTLSAddr],
                         "qGetTLSAddr", "get-thread-local-storage-address",
                         0);
This page took 0.031467 seconds and 4 git commands to generate.