diff mbox

[doc,RFA] New option: set print symbol-loading

Message ID 21305.48556.419222.690512@ruffy.mtv.corp.google.com
State Committed
Headers show

Commit Message

Doug Evans March 31, 2014, 7:10 p.m. UTC
Doug Evans writes:
 > On Wed, Feb 26, 2014 at 10:02 AM, Pedro Alves <palves@redhat.com> wrote:
 > > On 02/24/2014 11:50 PM, Doug Evans wrote:
 > >> +  if (print_symbol_loading_p (from_tty, 0, 0))
 > >> +    {
 > >> +      if (pattern != NULL)
 > >> +     printf_unfiltered (_("Loading symbols for shared libraries.\n"));
 > >> +      else
 > >> +     printf_unfiltered (_("Loading symbols for shared libraries: %s\n"),
 > >> +                        pattern);
 > >
 > > then/else looks reversed here.
 > 
 > Blech.  Thanks.

Here is what I committed.

2014-03-31  Doug Evans  <dje@google.com>

	New option "set print symbol-loading".
	* NEWS: Mention it.
	* solib.c (solib_read_symbols): Only print symbol loading messages
	if requested.
	(solib_add): If symbol loading is in "brief" mode, notify user
	symbols are being loaded.
	(reload_shared_libraries_1): Ditto.
	* symfile.c (print_symbol_loading_off): New static global.
	(print_symbol_loading_brief): New static global.
	(print_symbol_loading_full): New static global.
	(print_symbol_loading_enums): New static global.
	(print_symbol_loading): New static global.
	(print_symbol_loading_p): New function.
	(symbol_file_add_with_addrs): Only print symbol loading messages
	if requested.
	(_initialize_symfile): Register "print symbol-loading" set/show
	command.
	* symfile.h (print_symbol_loading_p): Declare.

	doc/
	* gdb.texinfo (Symbols): Document set/show print symbol-loading.

	testsuite/
	* gdb.base/print-symbol-loading-lib.c: New file.
	* gdb.base/print-symbol-loading-main.c: New file.
	* gdb.base/print-symbol-loading.exp: New file.
diff mbox

Patch

diff --git a/gdb/NEWS b/gdb/NEWS
index 2a384ba..df233fc 100644
--- a/gdb/NEWS
+++ b/gdb/NEWS
@@ -28,6 +28,13 @@  info auto-load guile-scripts [regexp]
 
 * New options
 
+set print symbol-loading (off|brief|full)
+show print symbol-loading
+  Control whether to print informational messages when loading symbol
+  information for a file.  The default is "full", but when debugging
+  programs with large numbers of shared libraries the amount of output
+  becomes less useful.
+
 set guile print-stack (none|message|full)
 show guile print-stack
   Show a stack trace when an error is encountered in a Guile script.
diff --git a/gdb/doc/gdb.texinfo b/gdb/doc/gdb.texinfo
index 0bf33b7..b218769 100644
--- a/gdb/doc/gdb.texinfo
+++ b/gdb/doc/gdb.texinfo
@@ -16184,6 +16184,28 @@  is printed as follows:
 @item show opaque-type-resolution
 Show whether opaque types are resolved or not.
 
+@kindex set print symbol-loading
+@cindex print messages when symbols are loaded
+@item set print symbol-loading
+@itemx set print symbol-loading full
+@itemx set print symbol-loading brief
+@itemx set print symbol-loading off
+The @code{set print symbol-loading} command allows you to control the
+printing of messages when @value{GDBN} loads symbol information.
+By default a message is printed for the executable and one for each
+shared library, and normally this is what you want.  However, when
+debugging apps with large numbers of shared libraries these messages
+can be annoying.
+When set to @code{brief} a message is printed for each executable,
+and when @value{GDBN} loads a collection of shared libraries at once
+it will only print one message regardless of the number of shared
+libraries.  When set to @code{off} no messages are printed.
+
+@kindex show print symbol-loading
+@item show print symbol-loading
+Show whether messages will be printed when a @value{GDBN} command
+entered from the keyboard causes symbol information to be loaded.
+
 @kindex maint print symbols
 @cindex symbol dump
 @kindex maint print psymbols
diff --git a/gdb/solib.c b/gdb/solib.c
index 3350bfd..e0afca0 100644
--- a/gdb/solib.c
+++ b/gdb/solib.c
@@ -650,7 +650,7 @@  solib_read_symbols (struct so_list *so, int flags)
 			   so->so_name);
       else
 	{
-	  if (from_tty || info_verbose)
+	  if (print_symbol_loading_p (from_tty, 0, 1))
 	    printf_unfiltered (_("Loaded symbols for %s\n"), so->so_name);
 	  so->symbols_loaded = 1;
 	}
@@ -905,6 +905,17 @@  solib_add (char *pattern, int from_tty,
 {
   struct so_list *gdb;
 
+  if (print_symbol_loading_p (from_tty, 0, 0))
+    {
+      if (pattern != NULL)
+	{
+	  printf_unfiltered (_("Loading symbols for shared libraries: %s\n"),
+			     pattern);
+	}
+      else
+	printf_unfiltered (_("Loading symbols for shared libraries.\n"));
+    }
+
   current_program_space->solib_add_generation++;
 
   if (pattern)
@@ -1277,6 +1288,9 @@  reload_shared_libraries_1 (int from_tty)
   struct so_list *so;
   struct cleanup *old_chain = make_cleanup (null_cleanup, NULL);
 
+  if (print_symbol_loading_p (from_tty, 0, 0))
+    printf_unfiltered (_("Loading symbols for shared libraries.\n"));
+
   for (so = so_list_head; so != NULL; so = so->next)
     {
       char *filename, *found_pathname = NULL;
diff --git a/gdb/symfile.c b/gdb/symfile.c
index aee7ef5..64a83c6 100644
--- a/gdb/symfile.c
+++ b/gdb/symfile.c
@@ -143,6 +143,20 @@  DEF_VEC_O (registered_sym_fns);
 
 static VEC (registered_sym_fns) *symtab_fns = NULL;
 
+/* Values for "set print symbol-loading".  */
+
+const char print_symbol_loading_off[] = "off";
+const char print_symbol_loading_brief[] = "brief";
+const char print_symbol_loading_full[] = "full";
+static const char *print_symbol_loading_enums[] =
+{
+  print_symbol_loading_off,
+  print_symbol_loading_brief,
+  print_symbol_loading_full,
+  NULL
+};
+static const char *print_symbol_loading = print_symbol_loading_full;
+
 /* If non-zero, shared library symbols will be added automatically
    when the inferior is created, new libraries are loaded, or when
    attaching to the inferior.  This is almost always what users will
@@ -156,6 +170,31 @@  static VEC (registered_sym_fns) *symtab_fns = NULL;
 int auto_solib_add = 1;
 
 
+/* Return non-zero if symbol-loading messages should be printed.
+   FROM_TTY is the standard from_tty argument to gdb commands.
+   If EXEC is non-zero the messages are for the executable.
+   Otherwise, messages are for shared libraries.
+   If FULL is non-zero then the caller is printing a detailed message.
+   E.g., the message includes the shared library name.
+   Otherwise, the caller is printing a brief "summary" message.  */
+
+int
+print_symbol_loading_p (int from_tty, int exec, int full)
+{
+  if (!from_tty && !info_verbose)
+    return 0;
+
+  if (exec)
+    {
+      /* We don't check FULL for executables, there are few such
+	 messages, therefore brief == full.  */
+      return print_symbol_loading != print_symbol_loading_off;
+    }
+  if (full)
+    return print_symbol_loading == print_symbol_loading_full;
+  return print_symbol_loading == print_symbol_loading_brief;
+}
+
 /* True if we are reading a symbol table.  */
 
 int currently_reading_symtab = 0;
@@ -1112,7 +1151,7 @@  symbol_file_add_with_addrs (bfd *abfd, const char *name, int add_flags,
   struct objfile *objfile;
   const int from_tty = add_flags & SYMFILE_VERBOSE;
   const int mainline = add_flags & SYMFILE_MAINLINE;
-  const int should_print = ((from_tty || info_verbose)
+  const int should_print = (print_symbol_loading_p (from_tty, mainline, 1)
 			    && (readnow_symbol_files
 				|| (add_flags & SYMFILE_NO_READ) == 0));
 
@@ -3985,4 +4024,18 @@  each global debug-file-directory component prepended."),
 				     NULL,
 				     show_debug_file_directory,
 				     &setlist, &showlist);
+
+  add_setshow_enum_cmd ("symbol-loading", no_class,
+			print_symbol_loading_enums, &print_symbol_loading,
+			_("\
+Set printing of symbol loading messages."), _("\
+Show printing of symbol loading messages."), _("\
+off   == turn all messages off\n\
+brief == print messages for the executable,\n\
+         and brief messages for shared libraries\n\
+full  == print messages for the executable,\n\
+         and messages for each shared library."),
+			NULL,
+			NULL,
+			&setprintlist, &showprintlist);
 }
diff --git a/gdb/symfile.h b/gdb/symfile.h
index 8e2569d..ff25028 100644
--- a/gdb/symfile.h
+++ b/gdb/symfile.h
@@ -503,6 +503,8 @@  extern bfd *gdb_bfd_open_maybe_remote (const char *);
 
 extern int get_section_index (struct objfile *, char *);
 
+extern int print_symbol_loading_p (int from_tty, int mainline, int full);
+
 /* Utility functions for overlay sections: */
 extern enum overlay_debugging_state
 {
diff --git a/gdb/testsuite/gdb.base/print-symbol-loading-lib.c b/gdb/testsuite/gdb.base/print-symbol-loading-lib.c
new file mode 100644
index 0000000..1e31e53
--- /dev/null
+++ b/gdb/testsuite/gdb.base/print-symbol-loading-lib.c
@@ -0,0 +1,21 @@ 
+/* Copyright 2010-2014 Free Software Foundation, Inc.
+
+   This file is part of GDB.
+
+   This program is free software; you can redistribute it and/or modify
+   it under the terms of the GNU General Public License as published by
+   the Free Software Foundation; either version 3 of the License, or
+   (at your option) any later version.
+
+   This program is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+
+   You should have received a copy of the GNU General Public License
+   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
+
+void
+lib (void)
+{
+}
diff --git a/gdb/testsuite/gdb.base/print-symbol-loading-main.c b/gdb/testsuite/gdb.base/print-symbol-loading-main.c
new file mode 100644
index 0000000..8379b58
--- /dev/null
+++ b/gdb/testsuite/gdb.base/print-symbol-loading-main.c
@@ -0,0 +1,25 @@ 
+/* Copyright 2010-2014 Free Software Foundation, Inc.
+
+   This file is part of GDB.
+
+   This program is free software; you can redistribute it and/or modify
+   it under the terms of the GNU General Public License as published by
+   the Free Software Foundation; either version 3 of the License, or
+   (at your option) any later version.
+
+   This program is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+
+   You should have received a copy of the GNU General Public License
+   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
+
+extern void lib (void);
+
+int
+main (void)
+{
+  lib ();
+  return 0;
+}
diff --git a/gdb/testsuite/gdb.base/print-symbol-loading.exp b/gdb/testsuite/gdb.base/print-symbol-loading.exp
new file mode 100644
index 0000000..a080ce1
--- /dev/null
+++ b/gdb/testsuite/gdb.base/print-symbol-loading.exp
@@ -0,0 +1,144 @@ 
+# Copyright 2012-2014 Free Software Foundation, Inc.
+
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program.  If not, see <http://www.gnu.org/licenses/>.
+
+# Test the "print symbol-loading" option.
+
+if {[skip_shlib_tests]} {
+    return 0
+}
+
+standard_testfile print-symbol-loading-main.c
+set libfile print-symbol-loading-lib
+set srcfile_lib ${libfile}.c
+set binfile_lib [standard_output_file ${libfile}.so]
+set gcorefile ${binfile}.gcore
+set objfile [standard_output_file ${testfile}.o]
+
+if { [gdb_compile_shlib ${srcdir}/${subdir}/${srcfile_lib} ${binfile_lib} {debug}] != ""
+     || [gdb_compile ${srcdir}/${subdir}/${srcfile} ${objfile} object {debug}] != "" } {
+    untested ${testfile}.exp
+    return -1
+}
+set opts [list debug shlib=${binfile_lib}]
+if { [gdb_compile ${objfile} ${binfile} executable $opts] != "" } {
+    untested ${testfile}.exp
+    return -1
+}
+
+clean_restart ${binfile}
+gdb_load_shlibs ${binfile_lib}
+
+# Does this gdb support gcore?
+set test "help gcore"
+gdb_test_multiple $test $test {
+    -re "Undefined command: .gcore.*\r\n$gdb_prompt $" {
+	# gcore command not supported -- nothing to test here.
+	unsupported "gdb does not support gcore on this target"
+	return -1
+    }
+    -re "Save a core file .*\r\n$gdb_prompt $" {
+	pass $test
+    }
+}
+
+if ![runto lib] {
+    return -1
+}
+
+if {![gdb_gcore_cmd $gcorefile "save a corefile"]} {
+    return -1
+}
+
+proc test_load_core { print_symbol_loading } {
+    global binfile binfile_lib gcorefile srcdir subdir
+    with_test_prefix "core ${print_symbol_loading}" {
+	gdb_exit
+	gdb_start
+	gdb_reinitialize_dir $srcdir/$subdir
+	gdb_test_no_output "set print symbol-loading $print_symbol_loading"
+	if { ${print_symbol_loading} != "off" } {
+	    gdb_test "file $binfile" "Reading symbols from.*done\\." "file"
+	} else {
+	    gdb_test_no_output "file $binfile" "file"
+	}
+	# Rename the shared lib so gdb can't find it.
+	remote_exec host "mv -f ${binfile_lib} ${binfile_lib}.save"
+	gdb_test "core ${gcorefile}" "Core was generated by .*" \
+	    "re-load generated corefile"
+	# Now put it back and use "set solib-search-path" to trigger
+	# loading of symbols.
+	remote_exec host "mv -f ${binfile_lib}.save ${binfile_lib}"
+	set test_name "load shared-lib"
+	switch "${print_symbol_loading}" {
+	    "off" {
+		gdb_test_no_output "set solib-search-path [file dirname ${binfile_lib}]" \
+		    ${test_name}
+	    }
+	    "brief" {
+		gdb_test "set solib-search-path [file dirname ${binfile_lib}]" \
+		    "Loading symbols for shared libraries\\." \
+		    ${test_name}
+	    }
+	    "full" {
+		gdb_test "set solib-search-path [file dirname ${binfile_lib}]" \
+		    "Reading symbols from.*Loaded symbols for.*" \
+		    ${test_name}
+	    }
+	}
+	gdb_test "frame" "#0 \[^\r\n\]* lib .*" "library got loaded"
+    }
+}
+
+test_load_core off
+test_load_core brief
+test_load_core full
+
+# Now test the sharedlibrary command.
+
+proc test_load_shlib { print_symbol_loading } {
+    global binfile
+    with_test_prefix "shlib ${print_symbol_loading}" {
+	clean_restart ${binfile}
+	gdb_test_no_output "set auto-solib-add off"
+	if ![runto_main] {
+	    return -1
+	}
+	gdb_test_no_output "set print symbol-loading $print_symbol_loading"
+	set test_name "load shared-lib"
+	switch ${print_symbol_loading} {
+	    "off" {
+		gdb_test_no_output "sharedlibrary .*" \
+		    ${test_name}
+	    }
+	    "brief" {
+		gdb_test "sharedlibrary .*" \
+		    "Loading symbols for shared libraries: \\.\\*" \
+		    ${test_name}
+	    }
+	    "full" {
+		gdb_test "sharedlibrary .*" \
+		    "Reading symbols from.*Loaded symbols for.*" \
+		    ${test_name}
+	    }
+	}
+	gdb_breakpoint "lib"
+	gdb_continue_to_breakpoint "lib"
+	gdb_test "frame" "#0 \[^\r\n\]* lib .*" "library got loaded"
+    }
+}
+
+test_load_shlib off
+test_load_shlib brief
+test_load_shlib full