Teach the testsuite that GDBserver reliably reports program exits.
[deliverable/binutils-gdb.git] / gdb / i386-linux-nat.c
index 11b510dc493ecc1a499622b7201e507cbbe1aa00..52ecc38f30f08d6d58fa6901a0ddfba259e0abe5 100644 (file)
@@ -25,6 +25,8 @@
 #include "regset.h"
 #include "target.h"
 #include "linux-nat.h"
+#include "linux-btrace.h"
+#include "btrace.h"
 
 #include "gdb_assert.h"
 #include "gdb_string.h"
@@ -146,9 +148,9 @@ fetch_register (struct regcache *regcache, int regno)
     }
 
   /* GNU/Linux LWP ID's are process ID's.  */
-  tid = TIDGET (inferior_ptid);
+  tid = ptid_get_lwp (inferior_ptid);
   if (tid == 0)
-    tid = PIDGET (inferior_ptid); /* Not a threaded program.  */
+    tid = ptid_get_pid (inferior_ptid); /* Not a threaded program.  */
 
   errno = 0;
   val = ptrace (PTRACE_PEEKUSER, tid,
@@ -174,9 +176,9 @@ store_register (const struct regcache *regcache, int regno)
     return;
 
   /* GNU/Linux LWP ID's are process ID's.  */
-  tid = TIDGET (inferior_ptid);
+  tid = ptid_get_lwp (inferior_ptid);
   if (tid == 0)
-    tid = PIDGET (inferior_ptid); /* Not a threaded program.  */
+    tid = ptid_get_pid (inferior_ptid); /* Not a threaded program.  */
 
   errno = 0;
   regcache_raw_collect (regcache, regno, &val);
@@ -512,9 +514,9 @@ i386_linux_fetch_inferior_registers (struct target_ops *ops,
     }
 
   /* GNU/Linux LWP ID's are process ID's.  */
-  tid = TIDGET (inferior_ptid);
+  tid = ptid_get_lwp (inferior_ptid);
   if (tid == 0)
-    tid = PIDGET (inferior_ptid); /* Not a threaded program.  */
+    tid = ptid_get_pid (inferior_ptid); /* Not a threaded program.  */
 
   /* Use the PTRACE_GETFPXREGS request whenever possible, since it
      transfers more registers in one system call, and we'll cache the
@@ -593,9 +595,9 @@ i386_linux_store_inferior_registers (struct target_ops *ops,
     }
 
   /* GNU/Linux LWP ID's are process ID's.  */
-  tid = TIDGET (inferior_ptid);
+  tid = ptid_get_lwp (inferior_ptid);
   if (tid == 0)
-    tid = PIDGET (inferior_ptid); /* Not a threaded program.  */
+    tid = ptid_get_pid (inferior_ptid); /* Not a threaded program.  */
 
   /* Use the PTRACE_SETFPXREGS requests whenever possible, since it
      transfers more registers in one system call.  But remember that
@@ -650,9 +652,9 @@ i386_linux_dr_get (ptid_t ptid, int regnum)
   int tid;
   unsigned long value;
 
-  tid = TIDGET (ptid);
+  tid = ptid_get_lwp (ptid);
   if (tid == 0)
-    tid = PIDGET (ptid);
+    tid = ptid_get_pid (ptid);
 
   errno = 0;
   value = ptrace (PTRACE_PEEKUSER, tid,
@@ -670,9 +672,9 @@ i386_linux_dr_set (ptid_t ptid, int regnum, unsigned long value)
 {
   int tid;
 
-  tid = TIDGET (ptid);
+  tid = ptid_get_lwp (ptid);
   if (tid == 0)
-    tid = PIDGET (ptid);
+    tid = ptid_get_pid (ptid);
 
   errno = 0;
   ptrace (PTRACE_POKEUSER, tid,
@@ -915,7 +917,7 @@ static void
 i386_linux_resume (struct target_ops *ops,
                   ptid_t ptid, int step, enum gdb_signal signal)
 {
-  int pid = PIDGET (ptid);
+  int pid = ptid_get_pid (ptid);
 
   int request;
 
@@ -998,9 +1000,9 @@ i386_linux_read_description (struct target_ops *ops)
   static uint64_t xcr0;
 
   /* GNU/Linux LWP ID's are process ID's.  */
-  tid = TIDGET (inferior_ptid);
+  tid = ptid_get_lwp (inferior_ptid);
   if (tid == 0)
-    tid = PIDGET (inferior_ptid); /* Not a threaded program.  */
+    tid = ptid_get_pid (inferior_ptid); /* Not a threaded program.  */
 
 #ifdef HAVE_PTRACE_GETFPXREGS
   if (have_ptrace_getfpxregs == -1)
@@ -1046,6 +1048,48 @@ i386_linux_read_description (struct target_ops *ops)
     return tdesc_i386_linux;
 }
 
+/* Enable branch tracing.  */
+
+static struct btrace_target_info *
+i386_linux_enable_btrace (ptid_t ptid)
+{
+  struct btrace_target_info *tinfo;
+  struct gdbarch *gdbarch;
+
+  errno = 0;
+  tinfo = linux_enable_btrace (ptid);
+
+  if (tinfo == NULL)
+    error (_("Could not enable branch tracing for %s: %s."),
+          target_pid_to_str (ptid), safe_strerror (errno));
+
+  /* Fill in the size of a pointer in bits.  */
+  gdbarch = target_thread_architecture (ptid);
+  tinfo->ptr_bits = gdbarch_ptr_bit (gdbarch);
+
+  return tinfo;
+}
+
+/* Disable branch tracing.  */
+
+static void
+i386_linux_disable_btrace (struct btrace_target_info *tinfo)
+{
+  int errcode = linux_disable_btrace (tinfo);
+
+  if (errcode != 0)
+    error (_("Could not disable branch tracing: %s."), safe_strerror (errcode));
+}
+
+/* Teardown branch tracing.  */
+
+static void
+i386_linux_teardown_btrace (struct btrace_target_info *tinfo)
+{
+  /* Ignore errors.  */
+  linux_disable_btrace (tinfo);
+}
+
 /* -Wmissing-prototypes */
 extern initialize_file_ftype _initialize_i386_linux_nat;
 
@@ -1079,6 +1123,13 @@ _initialize_i386_linux_nat (void)
 
   t->to_read_description = i386_linux_read_description;
 
+  /* Add btrace methods.  */
+  t->to_supports_btrace = linux_supports_btrace;
+  t->to_enable_btrace = i386_linux_enable_btrace;
+  t->to_disable_btrace = i386_linux_disable_btrace;
+  t->to_teardown_btrace = i386_linux_teardown_btrace;
+  t->to_read_btrace = linux_read_btrace;
+
   /* Register the target.  */
   linux_nat_add_target (t);
   linux_nat_set_new_thread (t, i386_linux_new_thread);
This page took 0.025747 seconds and 4 git commands to generate.