public inbox for systemtap@sourceware.org
 help / color / mirror / Atom feed
* [PATCH v4 1/3] systemtap/tapsets.cxx: Fix dwarfless probes on multiple static functions
@ 2015-04-20 10:30 Hemant Kumar
  2015-04-20 10:30 ` [RFC PATCH 2/3] Test " Hemant Kumar
                   ` (2 more replies)
  0 siblings, 3 replies; 11+ messages in thread
From: Hemant Kumar @ 2015-04-20 10:30 UTC (permalink / raw)
  To: systemtap
  Cc: mjw, naveen.n.rao, ulrich.weigand, uweigand, anton, fche, Hemant Kumar

With multiple static functions with same names in an ELF and in absence
of dwarf, if we probe on one of the functions, then systemtap places
probe only on one static function ignoring the rest. This is because the
mapping between the symbol names and their func_info is a simple map
which doesn't allow insertion of another symbol with the same name.

This patch fixes this issue by changing this map to a multimap which
allows duplicate entries for the same symbol name. lookup_symbol code
will return a set of func_info * instead of a single descriptor for a
function name.

We also need to fix other areas in the code where lookup_symbol() and
lookup_symbol_address() are being called so as to look for a set of
func_info's and a list of Dwarf_Addr's respectively, instead of a single
descriptor.

Signed-off-by: Hemant Kumar <hemant@linux.vnet.ibm.com>
---
 tapsets.cxx | 90 ++++++++++++++++++++++++++++++++++++++-----------------------
 1 file changed, 56 insertions(+), 34 deletions(-)

diff --git a/tapsets.cxx b/tapsets.cxx
index 443fb2e..c96c542 100644
--- a/tapsets.cxx
+++ b/tapsets.cxx
@@ -395,7 +395,7 @@ struct
 symbol_table
 {
   module_info *mod_info;	// associated module
-  map<string, func_info*> map_by_name;
+  multimap<string, func_info*> map_by_name;
   multimap<Dwarf_Addr, func_info*> map_by_addr;
   map<string, Dwarf_Addr> globals;
   map<string, Dwarf_Addr> locals;
@@ -410,8 +410,8 @@ symbol_table
   void prepare_section_rejection(Dwfl_Module *mod);
   bool reject_section(GElf_Word section);
   void purge_syscall_stubs();
-  func_info *lookup_symbol(const string& name);
-  Dwarf_Addr lookup_symbol_address(const string& name);
+  set <func_info*> *lookup_symbol(const string& name);
+  list <Dwarf_Addr> *lookup_symbol_address(const string& name);
   func_info *get_func_containing_address(Dwarf_Addr addr);
   func_info *get_first_func();
 
@@ -1113,9 +1113,15 @@ dwarf_query::query_module_symtab()
         }
       else
         {
-          fi = sym_table->lookup_symbol(function_str_val);
-          if (fi && !fi->descriptor && null_die(&fi->die))
-	     query_symtab_func_info(*fi, this);
+          set<func_info*> *fis = sym_table->lookup_symbol(function_str_val);
+          if (!fis || fis->empty())
+            return;
+          for (set<func_info*>::iterator it=fis->begin(); it!=fis->end(); ++it)
+            {
+              fi = *it;
+              if (fi && !fi->descriptor && null_die(&fi->die))
+                query_symtab_func_info(*fi, this);
+            }
         }
     }
 }
@@ -7484,8 +7490,8 @@ suggest_dwarf_functions(systemtap_session& sess,
       // add all function symbols in cache
       if (module->symtab_status != info_present || module->sym_table == NULL)
         continue;
-      map<string, func_info*>& modfuncs = module->sym_table->map_by_name;
-      for (map<string, func_info*>::const_iterator itfuncs = modfuncs.begin();
+      multimap<string, func_info*>& modfuncs = module->sym_table->map_by_name;
+      for (multimap<string, func_info*>::const_iterator itfuncs = modfuncs.begin();
            itfuncs != modfuncs.end(); ++itfuncs)
         funcs.insert(itfuncs->first);
     }
@@ -8072,9 +8078,8 @@ symbol_table::add_symbol(const char *name, bool weak, bool descriptor,
   fi->name = name;
   fi->weak = weak;
   fi->descriptor = descriptor;
-  map_by_name[fi->name] = fi;
-  // TODO: Use a multimap in case there are multiple static
-  // functions with the same name?
+
+  map_by_name.insert(make_pair(fi->name, fi));
   map_by_addr.insert(make_pair(addr, fi));
 }
 
@@ -8194,22 +8199,32 @@ symbol_table::get_first_func()
   return (iter)->second;
 }
 
-func_info *
+set <func_info*> *
 symbol_table::lookup_symbol(const string& name)
 {
-  map<string, func_info*>::iterator i = map_by_name.find(name);
-  if (i == map_by_name.end())
-    return NULL;
-  return i->second;
+  set<func_info*> *fis = new set<func_info*>;
+  pair <multimap<string, func_info*>::iterator, multimap<string, func_info*>::iterator> ret;
+  ret = map_by_name.equal_range(name);
+
+  for (multimap<string, func_info*>::iterator it = ret.first; it != ret.second; ++it)
+    fis->insert(it->second);
+
+  return fis;
 }
 
-Dwarf_Addr
+list <Dwarf_Addr> *
 symbol_table::lookup_symbol_address(const string& name)
 {
-  func_info *fi = lookup_symbol(name);
-  if (fi)
-    return fi->addr;
-  return 0;
+  list <Dwarf_Addr> *addrs = new list<Dwarf_Addr>;
+  set <func_info*> *fis = lookup_symbol(name);
+
+  if (!fis || fis->empty())
+    return NULL;
+
+  for (set<func_info*>::iterator it=fis->begin(); it!=fis->end(); ++it)
+    addrs->push_back((*it)->addr);
+
+  return addrs;
 }
 
 // This is the kernel symbol table.  The kernel macro cond_syscall creates
@@ -8223,9 +8238,12 @@ symbol_table::lookup_symbol_address(const string& name)
 void
 symbol_table::purge_syscall_stubs()
 {
-  Dwarf_Addr stub_addr = lookup_symbol_address("sys_ni_syscall");
-  if (stub_addr == 0)
+  list<Dwarf_Addr> *addrs = lookup_symbol_address("sys_ni_syscall");
+  if (!addrs || addrs->empty())
     return;
+  /* Highly unlikely that multiple symbols named "sys_ni_syscall" may exist */
+  Dwarf_Addr stub_addr = addrs->front();
+
   range_t purge_range = map_by_addr.equal_range(stub_addr);
   for (iterator_t iter = purge_range.first;
        iter != purge_range.second;
@@ -8299,21 +8317,25 @@ module_info::update_symtab(cu_function_cache_t *funcs)
       // missing, so we may also need to try matching by address.  See also the
       // notes about _Z in dwflpp::iterate_over_functions().
 
-      func_info *fi = sym_table->lookup_symbol(func->first);
-      if (!fi)
+      set<func_info*> *fis = sym_table->lookup_symbol(func->first);
+      if (!fis || fis->empty())
         continue;
 
-      // iterate over all functions at the same address
-      symbol_table::range_t er = sym_table->map_by_addr.equal_range(fi->addr);
-      for (symbol_table::iterator_t it = er.first; it != er.second; ++it)
+      for (set<func_info*>::iterator fi = fis->begin(); fi!=fis->end(); ++fi)
         {
-          // update this function with the dwarf die
-          it->second->die = func->second;
+          // iterate over all functions at the same address
+          symbol_table::range_t er = sym_table->map_by_addr.equal_range((*fi)->addr);
+
+          for (symbol_table::iterator_t it = er.first; it != er.second; ++it)
+            {
+              // update this function with the dwarf die
+              it->second->die = func->second;
 
-          // if this function is a new alias, then
-          // save it to merge into the function cache
-          if (it->second != fi)
-            new_funcs.insert(make_pair(it->second->name, it->second->die));
+              // if this function is a new alias, then
+              // save it to merge into the function cache
+              if (it->second != *fi)
+                new_funcs.insert(make_pair(it->second->name, it->second->die));
+            }
         }
     }
 
-- 
1.9.3

^ permalink raw reply	[flat|nested] 11+ messages in thread

end of thread, other threads:[~2015-04-24 19:33 UTC | newest]

Thread overview: 11+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2015-04-20 10:30 [PATCH v4 1/3] systemtap/tapsets.cxx: Fix dwarfless probes on multiple static functions Hemant Kumar
2015-04-20 10:30 ` [RFC PATCH 2/3] Test " Hemant Kumar
2015-04-20 11:18   ` Hemant Kumar
2015-04-22 21:21   ` Mark Wielaard
2015-04-20 10:31 ` [PATCH v4 3/3] Fix: Priotirize symbol table lookup for ppc64le Hemant Kumar
2015-04-22 13:48   ` Mark Wielaard
2015-04-22 14:30     ` Hemant Kumar
2015-04-22 13:40 ` [PATCH v4 1/3] systemtap/tapsets.cxx: Fix dwarfless probes on multiple static functions Mark Wielaard
2015-04-22 14:36   ` Hemant Kumar
2015-04-23 14:22     ` Mark Wielaard
2015-04-24 19:33       ` Mark Wielaard

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).