This is the mail archive of the gdb-patches@sources.redhat.com mailing list for the GDB 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]

[PATCH RFC] Use ui_out cleanups in cli-setshow.c


I've been seeing the following assertion failure in gdb:

    ../../src/gdb/ui-out.c:130: gdb-internal-error: push_level: Assertion
    `uiout->level >= 0 && uiout->level < MAX_UI_OUT_LEVELS' failed.

A simple way to generate this is to run the ``info set'' command.  A
rather long list is generated; when the "---Type <return> to continue,
or q <return> to quit---" prompt comes up, hit "q <return>".  Then
run the ``info set'' command again to see the assertion failure.

The reason that this happens is we're a couple of levels in in the
global uiout and returning to the top level doesn't pop the levels
correctly.

The patch below fixes cmd_show_list(), but I think there are many
other places in gdb that'll need similar fixes.  Basically, we have
to replace all calls to ui_out_tuple_begin with calls to
make_cleanup_ui_out_tuple_begin_end.  Then, later on, instead of
invoking ui_out_tuple_end, we'll instead invoke do_cleanups with the
cleanup chain generated from the earlier make_cleanup_...  call.

If this really is the case, I can't help but think that there's a better
way to structure the code.  Opinions?

	* cli/cli-setshow.c (cmd_show_list): Use cleanups to invoke
	ui_out_tuple_end().

Index: cli/cli-setshow.c
===================================================================
RCS file: /cvs/src/src/gdb/cli/cli-setshow.c,v
retrieving revision 1.8
diff -u -p -r1.8 cli-setshow.c
--- cli/cli-setshow.c	15 Jun 2002 18:45:32 -0000	1.8
+++ cli/cli-setshow.c	25 Jul 2002 19:22:02 -0000
@@ -354,28 +354,35 @@ do_setshow_command (char *arg, int from_
 void
 cmd_show_list (struct cmd_list_element *list, int from_tty, char *prefix)
 {
-  ui_out_tuple_begin (uiout, "showlist");
+  struct cleanup *showlist_chain;
+
+  showlist_chain = make_cleanup_ui_out_tuple_begin_end (uiout, "showlist");
   for (; list != NULL; list = list->next)
     {
       /* If we find a prefix, run its list, prefixing our output by its
          prefix (with "show " skipped).  */
       if (list->prefixlist && !list->abbrev_flag)
 	{
-	  ui_out_tuple_begin (uiout, "optionlist");
+	  struct cleanup *optionlist_chain
+	    = make_cleanup_ui_out_tuple_begin_end (uiout, "optionlist");
 	  ui_out_field_string (uiout, "prefix", list->prefixname + 5);
 	  cmd_show_list (*list->prefixlist, from_tty, list->prefixname + 5);
-	  ui_out_tuple_end (uiout);
+	  /* Invoke ui_out_tuple_end (uiout).  */
+	  do_cleanups (optionlist_chain);
 	}
       if (list->type == show_cmd)
 	{
-	  ui_out_tuple_begin (uiout, "option");
+	  struct cleanup *option_chain
+	    = make_cleanup_ui_out_tuple_begin_end (uiout, "option");
 	  ui_out_text (uiout, prefix);
 	  ui_out_field_string (uiout, "name", list->name);
 	  ui_out_text (uiout, ":  ");
 	  do_setshow_command ((char *) NULL, from_tty, list);
-	  ui_out_tuple_end (uiout);
+	  /* Invoke ui_out_tuple_end (uiout).  */
+	  do_cleanups (option_chain);
 	}
     }
-  ui_out_tuple_end (uiout);
+  /* Invoke ui_out_tuple_end (uiout).  */
+  do_cleanups (showlist_chain);
 }
 


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