From 0e14e0793ffb891bccd465cf518480685e3cd49e Mon Sep 17 00:00:00 2001 From: Josh Stone Date: Mon, 8 Jun 2009 15:36:42 -0700 Subject: Let query_module abort early for simple matches query_module was already returning DW_CB_ABORT when a simple match was found, but dwflpp::iterate_over_modules was ignoring that and instead forcing the module loop to restart. The only way out of the loop was with the pending_interrupts flag, which is only for signalled interrupts. Now iterate_over_modules will only attempt the dwfl_getmodules loop once, since that loop will only abort if the CB returns DW_CB_ABORT. Then query_module is also modified to return ABORT if pending_interrupts is flagged. My trusty test, stap -l syscall.*, is nearly 2x faster with this change. Empirically, I found that the kernel object is always the first "module" returned, so the syscall probepoints always gets to short-circuit the loop right away. --- tapsets.cxx | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'tapsets.cxx') diff --git a/tapsets.cxx b/tapsets.cxx index 50e80cf5..d8fe8f8e 100644 --- a/tapsets.cxx +++ b/tapsets.cxx @@ -1776,13 +1776,13 @@ query_module (Dwfl_Module *mod, // If we have enough information in the pattern to skip a module and // the module does not match that information, return early. if (!q->dw.module_name_matches(q->module_val)) - return DWARF_CB_OK; + return pending_interrupts ? DWARF_CB_ABORT : DWARF_CB_OK; // Don't allow module("*kernel*") type expressions to match the // elfutils module "kernel", which we refer to in the probe // point syntax exclusively as "kernel.*". if (q->dw.module_name == TOK_KERNEL && ! q->has_kernel) - return DWARF_CB_OK; + return pending_interrupts ? DWARF_CB_ABORT : DWARF_CB_OK; if (mod) validate_module_elf(mod, name, q); @@ -1810,7 +1810,7 @@ query_module (Dwfl_Module *mod, // If we know that there will be no more matches, abort early. - if (q->dw.module_name_final_match(q->module_val)) + if (q->dw.module_name_final_match(q->module_val) || pending_interrupts) return DWARF_CB_ABORT; else return DWARF_CB_OK; -- cgit