From 98a99cd3da5bc665e07a8f07b4b89815e89b8aa0 Mon Sep 17 00:00:00 2001 From: William Cohen Date: Thu, 15 May 2008 11:25:59 -0400 Subject: Add appropriate ChangeLog entry for earlier checkin. --- testsuite/systemtap.examples/ChangeLog | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/testsuite/systemtap.examples/ChangeLog b/testsuite/systemtap.examples/ChangeLog index 8d8c2ca1..41b70135 100644 --- a/testsuite/systemtap.examples/ChangeLog +++ b/testsuite/systemtap.examples/ChangeLog @@ -1,3 +1,9 @@ +2008-05-09 William Cohen + + * syscalls_by_pid.meta, syscalls_by_proc.meta: + * sigmon.meta, sig_by_pid.meta, sig_by_proc.meta: + * socket-trace.meta: New. + 2008-05-08 William Cohen * iotime.meta: New. -- cgit From 3972b443751ef6d0a441bae53ffa57d8a798aee4 Mon Sep 17 00:00:00 2001 From: David Smith Date: Thu, 15 May 2008 15:52:12 -0500 Subject: Ignores signals when removing the temporary directory. 2008-05-15 David Smith * main.cxx (setup_signals): New function. (main): Calls setup_signals() to setup signal handling. When removing the temporary directory, ignore signals. --- ChangeLog | 6 ++++++ main.cxx | 33 +++++++++++++++++++++++++++++---- 2 files changed, 35 insertions(+), 4 deletions(-) diff --git a/ChangeLog b/ChangeLog index 13f6254e..005af837 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,9 @@ +2008-05-15 David Smith + + * main.cxx (setup_signals): New function. + (main): Calls setup_signals() to setup signal handling. When + removing the temporary directory, ignore signals. + 2008-05-13 Ananth N Mavinakayanahalli PR 5955. * parse.cxx (parser::parse_global): accept ";" terminated globals diff --git a/main.cxx b/main.cxx index 2a1c0dfb..eadbd694 100644 --- a/main.cxx +++ b/main.cxx @@ -261,6 +261,30 @@ void handle_interrupt (int /* sig */) } +void +setup_signals (sighandler_t handler) +{ + struct sigaction sa; + + sa.sa_handler = handler; + sigemptyset (&sa.sa_mask); + if (handler != SIG_IGN) + { + sigaddset (&sa.sa_mask, SIGHUP); + sigaddset (&sa.sa_mask, SIGPIPE); + sigaddset (&sa.sa_mask, SIGINT); + sigaddset (&sa.sa_mask, SIGTERM); + } + sa.sa_flags = 0; + sa.sa_restorer = NULL; + + sigaction (SIGHUP, &sa, NULL); + sigaction (SIGPIPE, &sa, NULL); + sigaction (SIGINT, &sa, NULL); + sigaction (SIGTERM, &sa, NULL); +} + + int main (int argc, char * const argv []) { @@ -698,10 +722,7 @@ main (int argc, char * const argv []) // Set up our handler to catch routine signals, to allow clean // and reasonably timely exit. - signal (SIGHUP, handle_interrupt); - signal (SIGPIPE, handle_interrupt); - signal (SIGINT, handle_interrupt); - signal (SIGTERM, handle_interrupt); + setup_signals(&handle_interrupt); struct tms tms_before; times (& tms_before); @@ -1022,6 +1043,10 @@ pass_5: clog << "Keeping temporary directory \"" << s.tmpdir << "\"" << endl; else { + // Ignore signals while we're deleting the temporary directory. + setup_signals (SIG_IGN); + + // Remove the temporary directory. string cleanupcmd = "rm -rf "; cleanupcmd += s.tmpdir; if (s.verbose>1) clog << "Running " << cleanupcmd << endl; -- cgit From f4da2654099dc4e8bcabe15519078db9ca7650a4 Mon Sep 17 00:00:00 2001 From: "Frank Ch. Eigler" Date: Fri, 16 May 2008 11:04:05 -0400 Subject: note "make installcheck" in post-build checkout --- README | 1 + 1 file changed, 1 insertion(+) diff --git a/README b/README index addb7187..b36d7241 100644 --- a/README +++ b/README @@ -41,6 +41,7 @@ Build steps: ./configure --with-elfutils=PATCHED-ELFUTILS-DIR [other autoconf options] make all check sudo make install + sudo make installcheck Tips: -- cgit From 600db44c1ae1bb5b3b638dda1d8b25e14a332270 Mon Sep 17 00:00:00 2001 From: David Smith Date: Fri, 16 May 2008 14:51:07 -0500 Subject: Fixed PR 6499 (utrace probe crash). 2008-05-16 David Smith PR 6499. * task_finder.c (stap_register_task_finder_target): Added error check. (__stp_utrace_task_finder_report_clone): Ditto. (stap_utrace_detach_ops): Uses do_each_thread/while_each_thread instead of for_each_process (which only iterated among process group leaders instead of all threads). (stap_start_task_finder): Ditto. --- runtime/ChangeLog | 11 +++++++++++ runtime/task_finder.c | 32 ++++++++++++++++++-------------- 2 files changed, 29 insertions(+), 14 deletions(-) diff --git a/runtime/ChangeLog b/runtime/ChangeLog index aab6a862..bdf6e56d 100644 --- a/runtime/ChangeLog +++ b/runtime/ChangeLog @@ -1,3 +1,14 @@ +2008-05-16 David Smith + + PR 6499. + * task_finder.c (stap_register_task_finder_target): Added error + check. + (__stp_utrace_task_finder_report_clone): Ditto. + (stap_utrace_detach_ops): Uses do_each_thread/while_each_thread + instead of for_each_process (which only iterated among process + group leaders instead of all threads). + (stap_start_task_finder): Ditto. + 2008-05-08 David Smith PR 6500. diff --git a/runtime/task_finder.c b/runtime/task_finder.c index 2c27e4a3..e78caab6 100644 --- a/runtime/task_finder.c +++ b/runtime/task_finder.c @@ -44,6 +44,9 @@ stap_register_task_finder_target(struct stap_task_finder_target *new_tgt) struct stap_task_finder_target *tgt = NULL; int found_node = 0; + if (new_tgt == NULL) + return EFAULT; + if (new_tgt->pathname != NULL) new_tgt->pathlen = strlen(new_tgt->pathname); else @@ -85,13 +88,13 @@ stap_register_task_finder_target(struct stap_task_finder_target *new_tgt) static void stap_utrace_detach_ops(struct utrace_engine_ops *ops) { - struct task_struct *tsk; + struct task_struct *grp, *tsk; struct utrace_attached_engine *engine; long error = 0; pid_t pid = 0; rcu_read_lock(); - for_each_process(tsk) { + do_each_thread(grp, tsk) { struct mm_struct *mm; if (tsk->pid <= 1) @@ -106,7 +109,7 @@ stap_utrace_detach_ops(struct utrace_engine_ops *ops) error = -PTR_ERR(engine); if (error != ENOENT) { pid = tsk->pid; - break; + goto udo_err; } error = 0; } @@ -114,7 +117,8 @@ stap_utrace_detach_ops(struct utrace_engine_ops *ops) utrace_detach(tsk, engine); } } - } + } while_each_thread(grp, tsk); +udo_err: rcu_read_unlock(); if (error != 0) { @@ -322,7 +326,7 @@ __stp_utrace_task_finder_report_clone(struct utrace_attached_engine *engine, // Grab the path associated with the new task mmpath = __stp_get_mm_path(mm, mmpath_buf, PATH_MAX); mmput(mm); /* We're done with mm */ - if (IS_ERR(mmpath)) { + if (mmpath == NULL || IS_ERR(mmpath)) { rc = -PTR_ERR(mmpath); _stp_error("Unable to get path (error %d) for pid %d", rc, (int)child->pid); @@ -407,7 +411,7 @@ int stap_start_task_finder(void) { int rc = 0; - struct task_struct *tsk; + struct task_struct *grp, *tsk; char *mmpath_buf; mmpath_buf = _stp_kmalloc(PATH_MAX); @@ -419,13 +423,12 @@ stap_start_task_finder(void) atomic_set(&__stp_task_finder_state, __STP_TF_RUNNING); rcu_read_lock(); - for_each_process(tsk) { + do_each_thread(grp, tsk) { struct mm_struct *mm; char *mmpath; size_t mmpathlen; struct list_head *tgt_node; - /* Attach to the thread */ rc = __stp_utrace_attach(tsk, &__stp_utrace_task_finder_ops, 0, __STP_UTRACE_TASK_FINDER_EVENTS); if (rc == EPERM) { @@ -436,7 +439,7 @@ stap_start_task_finder(void) } else if (rc != 0) { /* If we get a real error, quit. */ - break; + goto stf_err; } /* Grab the path associated with this task. */ @@ -448,11 +451,11 @@ stap_start_task_finder(void) } mmpath = __stp_get_mm_path(mm, mmpath_buf, PATH_MAX); mmput(mm); /* We're done with mm */ - if (IS_ERR(mmpath)) { + if (mmpath == NULL || IS_ERR(mmpath)) { rc = -PTR_ERR(mmpath); _stp_error("Unable to get path (error %d) for pid %d", rc, (int)tsk->pid); - break; + goto stf_err; } /* Check the thread's exe's path/pid against our list. */ @@ -487,7 +490,7 @@ stap_start_task_finder(void) if (rc != 0) { _stp_error("attach callback for %d failed: %d", (int)tsk->pid, rc); - break; + goto stf_err; } // Set up thread death notification. @@ -495,11 +498,12 @@ stap_start_task_finder(void) cb_tgt, __STP_UTRACE_ATTACHED_TASK_EVENTS); if (rc != 0 && rc != EPERM) - break; + goto stf_err; cb_tgt->engine_attached = 1; } } - } + } while_each_thread(grp, tsk); + stf_err: rcu_read_unlock(); _stp_kfree(mmpath_buf); -- cgit From 6561773f763d40c00a115b53493ecf2d4f425d0d Mon Sep 17 00:00:00 2001 From: "Frank Ch. Eigler" Date: Fri, 16 May 2008 17:53:31 -0400 Subject: PR5643: function caching for much faster syscall.* pass-2 processing --- ChangeLog | 11 ++++++ elaborate.cxx | 5 ++- tapsets.cxx | 110 ++++++++++++++++++++++++++++++++++++++-------------------- 3 files changed, 87 insertions(+), 39 deletions(-) diff --git a/ChangeLog b/ChangeLog index 005af837..24fa8e3b 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,14 @@ +2008-05-16 Frank Ch. Eigler + + PR 5643 + * tapsets.cxx (cu_function_cache_t): Reorganize into + mod:cu->function->DIE lookup table. Consider merging into symtab + later. + (mark_dwarf_redudancies): Adapt. + (iterate_over_functions): Rewrite. + (dwarf_builder::build): Cache kprobes etc. symbol addresses. + * elaborate.cxx (systemtap_session ctor): Clear additional POD fields. + 2008-05-15 David Smith * main.cxx (setup_signals): New function. diff --git a/elaborate.cxx b/elaborate.cxx index 306baff1..0e454937 100644 --- a/elaborate.cxx +++ b/elaborate.cxx @@ -1188,7 +1188,10 @@ systemtap_session::systemtap_session (): hrtimer_derived_probes(0), perfmon_derived_probes(0), procfs_derived_probes(0), - op (0), up (0) + op (0), up (0), + sym_kprobes_text_start (0), + sym_kprobes_text_end (0), + sym_stext (0) { } diff --git a/tapsets.cxx b/tapsets.cxx index 9528066f..96a93019 100644 --- a/tapsets.cxx +++ b/tapsets.cxx @@ -535,7 +535,8 @@ module_cache }; typedef struct module_cache module_cache_t; -typedef map*> cu_function_cache_t; +typedef map cu_function_cache_t; +typedef map mod_cu_function_cache_t; // module:cu -> function -> die struct symbol_table @@ -1111,40 +1112,18 @@ struct dwflpp // ----------------------------------------------------------------- - cu_function_cache_t cu_function_cache; + mod_cu_function_cache_t cu_function_cache; static int cu_function_caching_callback (Dwarf_Die* func, void *arg) { - vector* v = static_cast*>(arg); - v->push_back (* func); + cu_function_cache_t* v = static_cast(arg); + string function_name = dwarf_diename(func); + (*v)[function_name] = * func; return DWARF_CB_OK; } int iterate_over_functions (int (* callback)(Dwarf_Die * func, void * arg), - void * data) - { - int rc = DWARF_CB_OK; - assert (module); - assert (cu); - - string key = module_name + ":" + cu_name; - vector* v = cu_function_cache[key]; - if (v == 0) - { - v = new vector; - cu_function_cache[key] = v; - dwarf_getfuncs (cu, cu_function_caching_callback, v, 0); - } - - for (unsigned i=0; isize(); i++) - { - Dwarf_Die die = v->at(i); - rc = (*callback)(& die, data); - if (rc != DWARF_CB_OK) break; - } - return rc; - } - + void * data); bool has_single_line_record (dwarf_query * q, char const * srcfile, int lineno); @@ -2489,6 +2468,58 @@ dwflpp::has_single_line_record (dwarf_query * q, char const * srcfile, int linen } +int +dwflpp::iterate_over_functions (int (* callback)(Dwarf_Die * func, void * arg), + void * data) +{ + int rc = DWARF_CB_OK; + assert (module); + assert (cu); + dwarf_query * q = static_cast(data); + + string key = module_name + ":" + cu_name; + cu_function_cache_t *v = cu_function_cache[key]; + if (v == 0) + { + v = new cu_function_cache_t; + cu_function_cache[key] = v; + dwarf_getfuncs (cu, cu_function_caching_callback, v, 0); + if (q->sess.verbose > 4) + clog << "function cache " << key << " size " << v->size() << endl; + } + + string subkey = q->function; + if (v->find(subkey) != v->end()) + { + Dwarf_Die die = v->at(subkey); + if (q->sess.verbose > 4) + clog << "function cache " << key << " hit " << subkey << endl; + return (*callback)(& die, data); + } + else if (name_has_wildcard (subkey)) + { + for (cu_function_cache_t::iterator it = v->begin(); it != v->end(); it++) + { + string func_name = it->first; + Dwarf_Die die = it->second; + if (function_name_matches_pattern (func_name, subkey)) + { + if (q->sess.verbose > 4) + clog << "function cache " << key << " match " << func_name << " vs " << subkey << endl; + + rc = (*callback)(& die, data); + if (rc != DWARF_CB_OK) break; + } + } + } + else // not a wildcard and no match in this CU + { + // do nothing + } + return rc; +} + + struct dwarf_builder: public derived_probe_builder { @@ -4584,10 +4615,13 @@ dwarf_builder::build(systemtap_session & sess, kern_dw->iterate_over_modules(&query_kernel_module, &km); if (km) { - sess.sym_kprobes_text_start = lookup_symbol_address (km, "__kprobes_text_start"); - sess.sym_kprobes_text_end = lookup_symbol_address (km, "__kprobes_text_end"); - sess.sym_stext = lookup_symbol_address (km, "_stext"); - + if (! sess.sym_kprobes_text_start) + sess.sym_kprobes_text_start = lookup_symbol_address (km, "__kprobes_text_start"); + if (! sess.sym_kprobes_text_end) + sess.sym_kprobes_text_end = lookup_symbol_address (km, "__kprobes_text_end"); + if (! sess.sym_stext) + sess.sym_stext = lookup_symbol_address (km, "_stext"); + if (sess.verbose > 2) { clog << "control symbols:" @@ -4774,21 +4808,21 @@ symbol_table::mark_dwarf_redundancies(dwflpp *dw) // vector of Dwarf_Dies, one per function. string module_prefix = string(mod_info->name) + ":"; - cu_function_cache_t::iterator cu; + mod_cu_function_cache_t::iterator cu; for (cu = dw->cu_function_cache.begin(); - cu != dw->cu_function_cache.end(); cu++) + cu != dw->cu_function_cache.end(); cu++) { string key = cu->first; if (key.find(module_prefix) == 0) { // Found a compilation unit in the module of interest. // Mark all its functions in the symbol table. - vector* v = cu->second; + cu_function_cache_t* v = cu->second; assert(v); - for (unsigned f=0; f < v->size(); f++) + for (cu_function_cache_t::iterator fc = v->begin(); fc != v->end(); fc++) { - Dwarf_Die func = v->at(f); - string func_name = dwarf_diename(&func); + Dwarf_Die func = fc->second; + string func_name = fc->first; // == dwarf_diename(&func); // map_by_name[func_name]->die = func; map::iterator i = map_by_name.find(func_name); // Func names can show up in the dwarf but not the symtab (!). -- cgit From 2171f774be4c06664c5d2a0c1b8ef1f8b870ffdb Mon Sep 17 00:00:00 2001 From: "Frank Ch. Eigler" Date: Sat, 17 May 2008 08:52:19 -0400 Subject: make the mod_cu_function_cache a hash_map instead of map for more go-go --- ChangeLog | 5 +++++ tapsets.cxx | 12 +++++++++--- 2 files changed, 14 insertions(+), 3 deletions(-) diff --git a/ChangeLog b/ChangeLog index 24fa8e3b..139ae6ac 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,8 @@ +2008-05-17 Frank Ch. Eigler + + * tapsets.cxx (cu_function_cache_t): Switch to s, + since these tables tend to get pretty big. + 2008-05-16 Frank Ch. Eigler PR 5643 diff --git a/tapsets.cxx b/tapsets.cxx index 96a93019..c8f77fde 100644 --- a/tapsets.cxx +++ b/tapsets.cxx @@ -20,6 +20,7 @@ #include #include #include +#include #include #include #include @@ -54,6 +55,7 @@ extern "C" { #endif using namespace std; +using namespace __gnu_cxx; // ------------------------------------------------------------------------ @@ -535,8 +537,12 @@ module_cache }; typedef struct module_cache module_cache_t; -typedef map cu_function_cache_t; -typedef map mod_cu_function_cache_t; // module:cu -> function -> die +struct stringhash { + size_t operator() (const string& s) const { hash h; return h(s.c_str()); } +}; + +typedef hash_map cu_function_cache_t; +typedef hash_map mod_cu_function_cache_t; // module:cu -> function -> die struct symbol_table @@ -2491,7 +2497,7 @@ dwflpp::iterate_over_functions (int (* callback)(Dwarf_Die * func, void * arg), string subkey = q->function; if (v->find(subkey) != v->end()) { - Dwarf_Die die = v->at(subkey); + Dwarf_Die die = v->find(subkey)->second; if (q->sess.verbose > 4) clog << "function cache " << key << " hit " << subkey << endl; return (*callback)(& die, data); -- cgit From 277f2b79b02bf69a1d72d05b06086b07bcc6a113 Mon Sep 17 00:00:00 2001 From: "Frank Ch. Eigler" Date: Sat, 17 May 2008 10:02:19 -0400 Subject: suppress "pass-2 failed" messages from "stap -l FOOBAR"; just produce empty output --- ChangeLog | 6 ++++++ elaborate.cxx | 9 +++------ main.cxx | 2 +- 3 files changed, 10 insertions(+), 7 deletions(-) diff --git a/ChangeLog b/ChangeLog index 139ae6ac..92aad43b 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,9 @@ +2008-05-17 Frank Ch. Eigler + + * elaborate.cxx (semantic_pass): Error on #probes=0, but not in + listing mode. + (semantic_pass_optimize[12]): Remove inappropriate check from here. + 2008-05-17 Frank Ch. Eigler * tapsets.cxx (cu_function_cache_t): Switch to s, diff --git a/elaborate.cxx b/elaborate.cxx index 0e454937..9a817cba 100644 --- a/elaborate.cxx +++ b/elaborate.cxx @@ -1159,6 +1159,9 @@ semantic_pass (systemtap_session& s) if (rc == 0 && ! s.unoptimized) rc = semantic_pass_optimize2 (s); if (rc == 0) rc = semantic_pass_vars (s); if (rc == 0) rc = semantic_pass_stats (s); + + if (s.probes.size() == 0 && !s.listing_mode) + throw semantic_error ("no probes found"); } catch (const semantic_error& e) { @@ -2139,9 +2142,6 @@ semantic_pass_optimize1 (systemtap_session& s) semantic_pass_opt4 (s, relaxed_p); } - if (s.probes.size() == 0) - throw semantic_error ("no probes found"); - return rc; } @@ -2164,9 +2164,6 @@ semantic_pass_optimize2 (systemtap_session& s) semantic_pass_opt5 (s, relaxed_p); } - if (s.probes.size() == 0) - throw semantic_error ("no probes found"); - return rc; } diff --git a/main.cxx b/main.cxx index eadbd694..b53499b7 100644 --- a/main.cxx +++ b/main.cxx @@ -242,7 +242,7 @@ printscript(systemtap_session& s, ostream& o) } } } - } +} int pending_interrupts; -- cgit