This is the mail archive of the archer@sourceware.org mailing list for the Archer project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[python] fix PR 10615


I'm checking this in on the python branch.

This fixes PR 10615, a bug where a change to a struct-valued child of a
dynamic varobj would not properly be reported by -var-update.

Tom

2009-09-09  Tom Tromey  <tromey@redhat.com>

	PR mi/10615:
	* varobj.c (install_dynamic_child): Add 'unchanged' argument.
	(update_dynamic_varobj_children): Likewise.
	(varobj_get_num_children): Update.
	(varobj_list_children): Update.
	(varobj_update): Add unchanged children to update list.

2009-09-09  Tom Tromey  <tromey@redhat.com>

	* gdb.python/python-prettyprint.c (struct substruct): New type.
	(struct outerstruct): Likewise.
	(substruct_test): New function.
	(main): Call it.
	* gdb.python/python-mi.exp: Add regression tests.
	* gdb.python/python-prettyprint.py (pp_outer): New class.
	(register_pretty_printers): Update.

diff --git a/gdb/testsuite/gdb.python/python-mi.exp b/gdb/testsuite/gdb.python/python-mi.exp
index 7791775..0178270 100644
--- a/gdb/testsuite/gdb.python/python-mi.exp
+++ b/gdb/testsuite/gdb.python/python-mi.exp
@@ -192,6 +192,29 @@ mi_varobj_update_dynamic container \
   }
 
 mi_continue_to_line \
+    [gdb_get_line_number {MI outer breakpoint here} ${testfile}.c] \
+    "step to outer breakpoint"
+
+mi_create_dynamic_varobj outer outer \
+  "create outer varobj"
+
+mi_list_varobj_children outer {
+  { outer.s s 2 "struct substruct" }
+  { outer.x x 0 "int" }
+} "list children of outer"
+
+mi_list_varobj_children outer.s {
+  { outer.s.a a 0 int }
+  { outer.s.b b 0 int }
+} "list children of outer.s"
+
+mi_next "next over outer update"
+
+mi_gdb_test "-var-update outer" \
+  ".done,changelist=.{name=\"outer.s.a\",in_scope=\"true\",type_changed=\"false\",has_more=\"0\"}." \
+  "update after updating element of outer"
+
+mi_continue_to_line \
     [gdb_get_line_number {Another MI breakpoint} ${testfile}.c] \
     "step to second breakpoint"
 
diff --git a/gdb/testsuite/gdb.python/python-prettyprint.c b/gdb/testsuite/gdb.python/python-prettyprint.c
index adf66b5..bf41ebc 100644
--- a/gdb/testsuite/gdb.python/python-prettyprint.c
+++ b/gdb/testsuite/gdb.python/python-prettyprint.c
@@ -82,6 +82,29 @@ class Derived : public Vbase1, public Vbase2, public Vbase3
 
 #endif
 
+struct substruct {
+  int a;
+  int b;
+};
+
+struct outerstruct {
+  struct substruct s;
+  int x;
+};
+
+struct outerstruct
+substruct_test (void)
+{
+  struct outerstruct outer;
+  outer.s.a = 0;
+  outer.s.b = 0;
+  outer.x = 0;
+
+  outer.s.a = 3;		/* MI outer breakpoint here */
+
+  return outer;  
+}
+
 typedef struct string_repr
 {
   struct whybother
@@ -212,6 +235,8 @@ main ()
 
   add_item (&c2, 2222);
   add_item (&c2, 3333);
+
+  substruct_test ();
   do_nothing ();
 #endif
 
diff --git a/gdb/testsuite/gdb.python/python-prettyprint.py b/gdb/testsuite/gdb.python/python-prettyprint.py
index c3e0dc4..2f070d8 100644
--- a/gdb/testsuite/gdb.python/python-prettyprint.py
+++ b/gdb/testsuite/gdb.python/python-prettyprint.py
@@ -112,6 +112,19 @@ class pp_ns:
     def display_hint (self):
         return 'string'
 
+class pp_outer:
+    "Print struct outer"
+
+    def __init__ (self, val):
+        self.val = val
+
+    def to_string (self):
+        return "x = %s" % self.val['x']
+
+    def children (self):
+        yield 's', self.val['s']
+        yield 'x', self.val['x']
+
 def lookup_function (val):
     "Look-up and return a pretty-printer that can print val."
 
@@ -170,6 +183,10 @@ def register_pretty_printers ():
     
     pretty_printers_dict[re.compile ('^struct ns$')]  = pp_ns
     pretty_printers_dict[re.compile ('^ns$')]  = pp_ns
+
+    pretty_printers_dict[re.compile ('^struct outerstruct$')]  = pp_outer
+    pretty_printers_dict[re.compile ('^outerstruct$')]  = pp_outer
+
 pretty_printers_dict = {}
 
 register_pretty_printers ()
diff --git a/gdb/varobj.c b/gdb/varobj.c
index e1dec23..7dad226 100644
--- a/gdb/varobj.c
+++ b/gdb/varobj.c
@@ -899,6 +899,7 @@ static void
 install_dynamic_child (struct varobj *var,
 		       VEC (varobj_p) **changed,
 		       VEC (varobj_p) **new,
+		       VEC (varobj_p) **unchanged,
 		       int *cchanged,
 		       int index,
 		       const char *name,
@@ -920,6 +921,8 @@ install_dynamic_child (struct varobj *var,
 	  if (changed)
 	    VEC_safe_push (varobj_p, *changed, existing);
 	}
+      else if (unchanged)
+	VEC_safe_push (varobj_p, *unchanged, existing);
     }
 }
 
@@ -944,6 +947,7 @@ static int
 update_dynamic_varobj_children (struct varobj *var,
 				VEC (varobj_p) **changed,
 				VEC (varobj_p) **new,
+				VEC (varobj_p) **unchanged,
 				int *cchanged,
 				int update_children,
 				int to)
@@ -1027,7 +1031,7 @@ update_dynamic_varobj_children (struct varobj *var,
 	    error (_("Invalid item from the child list"));
 
 	  v = convert_value_from_python (py_v);
-	  install_dynamic_child (var, changed, new,
+	  install_dynamic_child (var, changed, new, unchanged,
 				 cchanged, i, name, v);
 	  do_cleanups (inner);
 	}
@@ -1077,7 +1081,7 @@ varobj_get_num_children (struct varobj *var)
 
 	  /* If we have a dynamic varobj, don't report -1 children.
 	     So, try to fetch some children first.  */
-	  update_dynamic_varobj_children (var, NULL, NULL, &dummy, 0, 0);
+	  update_dynamic_varobj_children (var, NULL, NULL, NULL, &dummy, 0, 0);
 	}
       else
 	var->num_children = number_of_children (var);
@@ -1103,7 +1107,7 @@ varobj_list_children (struct varobj *var, int *from, int *to)
       /* This, in theory, can result in the number of children changing without
 	 frontend noticing.  But well, calling -var-list-children on the same
 	 varobj twice is not something a sane frontend would do.  */
-      update_dynamic_varobj_children (var, NULL, NULL, &children_changed,
+      update_dynamic_varobj_children (var, NULL, NULL, NULL, &children_changed,
 				      0, *to);
       restrict_range (var->children, from, to);
       return var->children;
@@ -1739,7 +1743,7 @@ VEC(varobj_update_result) *varobj_update (struct varobj **varp, int explicit)
 	 invoked.    */
       if (v->pretty_printer)
 	{
-	  VEC (varobj_p) *changed = 0, *new = 0;
+	  VEC (varobj_p) *changed = 0, *new = 0, *unchanged = 0;
 	  int i, children_changed;
 	  varobj_p tmp;
 
@@ -1758,7 +1762,8 @@ VEC(varobj_update_result) *varobj_update (struct varobj **varp, int explicit)
 		 it.  */
 	      if (!varobj_has_more (v, 0))
 		{
-		  update_dynamic_varobj_children (v, NULL, NULL, &dummy, 0, 0);
+		  update_dynamic_varobj_children (v, NULL, NULL, NULL,
+						  &dummy, 0, 0);
 		  if (varobj_has_more (v, 0))
 		    r.changed = 1;
 		}
@@ -1771,7 +1776,7 @@ VEC(varobj_update_result) *varobj_update (struct varobj **varp, int explicit)
 
 	  /* If update_dynamic_varobj_children returns 0, then we have
 	     a non-conforming pretty-printer, so we skip it.  */
-	  if (update_dynamic_varobj_children (v, &changed, &new,
+	  if (update_dynamic_varobj_children (v, &changed, &new, &unchanged,
 					      &children_changed, 1, v->to))
 	    {
 	      if (children_changed || new)
@@ -1786,12 +1791,22 @@ VEC(varobj_update_result) *varobj_update (struct varobj **varp, int explicit)
 		  r.value_installed = 1;
 		  VEC_safe_push (varobj_update_result, stack, &r);
 		}
+	      for (i = 0; VEC_iterate (varobj_p, unchanged, i, tmp); ++i)
+	      	{
+	      	  if (!tmp->frozen)
+	      	    {
+	      	      varobj_update_result r = {tmp};
+	      	      r.value_installed = 1;
+	      	      VEC_safe_push (varobj_update_result, stack, &r);
+	      	    }
+	      	}
 	      if (r.changed || r.children_changed)
 		VEC_safe_push (varobj_update_result, result, &r);
 
-	      /* Free CHANGED, but not NEW, because NEW has been put
-		 into the result vector.  */
+	      /* Free CHANGED and UNCHANGED, but not NEW, because NEW
+		 has been put into the result vector.  */
 	      VEC_free (varobj_p, changed);
+	      VEC_free (varobj_p, unchanged);
 
 	      continue;
 	    }


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]