[v2,04/12] btrace: Handle stepping and goto for auxiliary instructions.

Message ID 20210614145025.688566-5-felix.willgerodt@intel.com
State Superseded
Headers show
Series
  • Extensions for PTWRITE
Related show

Commit Message

Print the auxiliary data when stepping. Don't allow to goto an auxiliary
instruction.

This patch is in preparation for the new ptwrite feature, which is based on
auxiliary instructions.

gdb/ChangeLog:
2021-06-14  Felix Willgerodt  <felix.willgerodt@intel.com>

	* record-btrace.c: (record_btrace_single_step_forward): Handle
	BTRACE_INSN_AUX.
	(record_btrace_single_step_backward): Likewise.
	(record_btrace_goto): Likewise.
---
 gdb/record-btrace.c | 66 ++++++++++++++++++++++++++++++++++++---------
 1 file changed, 53 insertions(+), 13 deletions(-)

-- 
2.25.4

Intel Deutschland GmbH
Registered Address: Am Campeon 10, 85579 Neubiberg, Germany
Tel: +49 89 99 8853-0, www.intel.de <http://www.intel.de>
Managing Directors: Christin Eisenschmid, Sharon Heck, Tiffany Doon Silva  
Chairperson of the Supervisory Board: Nicole Lau
Registered Office: Munich
Commercial Register: Amtsgericht Muenchen HRB 186928

Patch

diff --git a/gdb/record-btrace.c b/gdb/record-btrace.c
index 2fc273ca229..3d0c344e8e6 100644
--- a/gdb/record-btrace.c
+++ b/gdb/record-btrace.c
@@ -2377,6 +2377,7 @@  record_btrace_single_step_forward (struct thread_info *tp)
 {
   struct btrace_insn_iterator *replay, end, start;
   struct btrace_thread_info *btinfo;
+  struct btrace_insn next_insn;
 
   btinfo = &tp->btrace;
   replay = btinfo->replay;
@@ -2390,9 +2391,13 @@  record_btrace_single_step_forward (struct thread_info *tp)
     return btrace_step_stopped ();
 
   /* Skip gaps during replay.  If we end up at a gap (at the end of the trace),
-     jump back to the instruction at which we started.  */
+     jump back to the instruction at which we started.  If we're stepping a
+     BTRACE_INSN_AUX instruction, print the auxiliary data and skip the
+     instruction.  */
+
   start = *replay;
-  do
+
+  for (;;)
     {
       unsigned int steps;
 
@@ -2400,12 +2405,25 @@  record_btrace_single_step_forward (struct thread_info *tp)
 	 of the execution history.  */
       steps = btrace_insn_next (replay, 1);
       if (steps == 0)
+        {
+          *replay = start;
+          return btrace_step_no_history ();
+        }
+
+      const struct btrace_insn *insn = btrace_insn_get (replay);
+
+      /* If we're stepping a BTRACE_INSN_AUX instruction, print the auxiliary
+	 data and skip the instruction.  */
+      if (insn->iclass == BTRACE_INSN_AUX)
 	{
-	  *replay = start;
-	  return btrace_step_no_history ();
+	  printf_unfiltered ("[%s]\n",
+			     btinfo->aux_data[insn->aux_data_index].c_str ());
+	  continue;
 	}
+
+      if (insn != NULL)
+	break;
     }
-  while (btrace_insn_get (replay) == NULL);
 
   /* Determine the end of the instruction trace.  */
   btrace_insn_end (&end, btinfo);
@@ -2426,6 +2444,7 @@  record_btrace_single_step_backward (struct thread_info *tp)
 {
   struct btrace_insn_iterator *replay, start;
   struct btrace_thread_info *btinfo;
+  struct btrace_insn prev_insn;
 
   btinfo = &tp->btrace;
   replay = btinfo->replay;
@@ -2436,9 +2455,12 @@  record_btrace_single_step_backward (struct thread_info *tp)
 
   /* If we can't step any further, we reached the end of the history.
      Skip gaps during replay.  If we end up at a gap (at the beginning of
-     the trace), jump back to the instruction at which we started.  */
+     the trace), jump back to the instruction at which we started.
+     If we're stepping a BTRACE_INSN_AUX instruction, print the auxiliary
+     data and skip the instruction.  */
   start = *replay;
-  do
+
+  for (;;)
     {
       unsigned int steps;
 
@@ -2448,8 +2470,20 @@  record_btrace_single_step_backward (struct thread_info *tp)
 	  *replay = start;
 	  return btrace_step_no_history ();
 	}
+
+      const struct btrace_insn *insn = btrace_insn_get (replay);
+
+      /* Check if we're stepping a BTRACE_INSN_AUX instruction and skip it.  */
+      if (insn->iclass == BTRACE_INSN_AUX)
+	{
+	  printf_unfiltered ("[%s]\n",
+			     btinfo->aux_data[insn->aux_data_index].c_str ());
+	  continue;
+	}
+
+      if (insn != NULL)
+	break;
     }
-  while (btrace_insn_get (replay) == NULL);
 
   /* Check if we're stepping a breakpoint.
 
@@ -2872,25 +2906,31 @@  record_btrace_target::goto_record_end ()
 /* The goto_record method of target record-btrace.  */
 
 void
-record_btrace_target::goto_record (ULONGEST insn)
+record_btrace_target::goto_record (ULONGEST insn_number)
 {
   struct thread_info *tp;
   struct btrace_insn_iterator it;
   unsigned int number;
   int found;
 
-  number = insn;
+  number = insn_number;
 
   /* Check for wrap-arounds.  */
-  if (number != insn)
+  if (number != insn_number)
     error (_("Instruction number out of range."));
 
   tp = require_btrace_thread ();
 
   found = btrace_find_insn_by_number (&it, &tp->btrace, number);
 
-  /* Check if the instruction could not be found or is a gap.  */
-  if (found == 0 || btrace_insn_get (&it) == NULL)
+  /* Check if the instruction could not be found or is a gap or an
+     auxilliary instruction.  */
+  if (found == 0)
+    error (_("No such instruction."));
+
+  const struct btrace_insn *insn = btrace_insn_get (&it);
+
+  if ((insn == NULL) || (insn->iclass == BTRACE_INSN_AUX))
     error (_("No such instruction."));
 
   record_btrace_set_replay (tp, &it);