Addition of GDB server monitor command 'v.info execontext' that shows
information about the stack traces recorded by Valgrind.
This can be used to analyse one possible cause of Valgrind high
memory usage for some programs.

At work, a big set of regression tests crashed out of memory under Valgrind.

Two main causes for out of memory were identified:
1. big memory usage for stacktrace (exe contexts) recording by Valgrind
2. big number of partially initialised bytes.

This patch adds a gdbsrv monitor command that output (very) detailed
information about all the recorded exe context.

This has been used to analyse the problem 1. above,
showing the following identified causes for a (too) big nr of execontexts:

A. When the JIT handles an unknown SP update, even when --track-origins=no,
an execontext is (uselessly) created and recorded
to track the (never used) origin of some uninitialised stack memory.
This creates a whole bunch of 'one IP' execontexts.

B. same problem in handling some system calls (at least the brk system
 calls always records an origin, even when --track-origins=yes).

C. The Valgrind unwinder cannot properly unwind some stack traces.
  It unwinds a few frames, then go bezerk and stops at a "random" IP.
  This then causes the same "logical" stacktrace to be truncated
  and records thousands of times with this "differentiating" last IP.


For problem cause 2 above ( a lot of partially initialised bytes),
the idea is to similarly add another gdbsrv commands that will output
statistics about which stack traces are causing a lot of uninitialised bytes. 




git-svn-id: svn://svn.valgrind.org/valgrind/trunk@13220 a5019735-40e9-0310-863c-91ae7b9d1cf9
diff --git a/coregrind/m_gdbserver/server.c b/coregrind/m_gdbserver/server.c
index 1e9ee30..90340a6 100644
--- a/coregrind/m_gdbserver/server.c
+++ b/coregrind/m_gdbserver/server.c
@@ -27,6 +27,7 @@
 #include "pub_core_translate.h"
 #include "pub_core_mallocfree.h"
 #include "pub_core_initimg.h"
+#include "pub_core_execontext.h"
 #include "pub_core_syswrap.h"      // VG_(show_open_fds)
 
 unsigned long cont_thread;
@@ -177,6 +178,7 @@
 "  v.info gdbserver_status : show gdbserver status\n"
 "  v.info memory [aspacemgr] : show valgrind heap memory stats\n"
 "     (with aspacemgr arg, also shows valgrind segments on log ouput)\n"
+"  v.info exectxt          : show stacktraces and stats of all execontexts\n"
 "  v.info scheduler        : show valgrind thread state and stacktrace\n"
 "  v.set debuglog <level>  : set valgrind debug log level to <level>\n"
 "  v.translate <addr> [<traceflags>]  : debug translation of <addr> with <traceflags>\n"
@@ -243,7 +245,7 @@
       wcmd = strtok_r (NULL, " ", &ssaveptr);
       switch (kwdid = VG_(keyword_id) 
               ("all_errors n_errs_found last_error gdbserver_status memory"
-               " scheduler open_fds",
+               " scheduler open_fds exectxt",
                wcmd, kwd_report_all)) {
       case -2:
       case -1: 
@@ -295,6 +297,10 @@
                 " to show open fds\n");
          ret = 1;
          break;
+      case  7: /* exectxt */
+         VG_(print_ExeContext_stats) (True /* with_stacktraces */);
+         ret = 1;
+         break;
       default:
          vg_assert(0);
       }