diff options
-rw-r--r-- | includes/sys/sdt.h | 9 | ||||
-rw-r--r-- | tapset-utrace.cxx | 109 | ||||
-rw-r--r-- | tapsets.cxx | 77 | ||||
-rw-r--r-- | testsuite/systemtap.apps/postgres.exp | 9 | ||||
-rw-r--r-- | testsuite/systemtap.base/sdt.exp | 4 | ||||
-rw-r--r-- | testsuite/systemtap.base/sdt_misc.exp | 4 |
6 files changed, 40 insertions, 172 deletions
diff --git a/includes/sys/sdt.h b/includes/sys/sdt.h index 7c23d55a..882a0d8b 100644 --- a/includes/sys/sdt.h +++ b/includes/sys/sdt.h @@ -1,4 +1,4 @@ -/* Copyright (C) 2005-2009 Red Hat Inc. +/* Copyright (C) 2005-2010 Red Hat Inc. This file is part of systemtap, and is free software in the public domain. */ @@ -49,7 +49,7 @@ #define STAP_SEMAPHORE(probe) #endif -#if ! (defined EXPERIMENTAL_UTRACE_SDT || defined EXPERIMENTAL_KPROBE_SDT) +#if ! defined EXPERIMENTAL_KPROBE_SDT /* These baroque macros are used to create a unique label. */ #define STAP_CONCAT(a,b) a ## b @@ -222,7 +222,7 @@ do STAP_SEMAPHORE(probe) { \ STAP_NOP "/* %0 %1 %2 %3 %4 %5 %6 %7 %8 %9 */" :: "g"(arg1), "g"(arg2), "g"(arg3), "g"(arg4), "g"(arg5), "g"(arg6), "g"(arg7), "g"(arg8), "g"(arg9), "g"(arg10)); \ } while (0) -#else /* ! (defined EXPERIMENTAL_UTRACE_SDT || defined EXPERIMENTAL_KPROBE_SDT) */ +#else /* ! defined EXPERIMENTAL_KPROBE_SDT */ #include <unistd.h> #include <sys/syscall.h> # if defined (__USE_ANSI) @@ -231,9 +231,6 @@ extern long int syscall (long int __sysno, ...) __THROW; # if defined EXPERIMENTAL_KPROBE_SDT # define STAP_SYSCALL __NR_getegid # define STAP_GUARD 0x32425250 -# elif defined EXPERIMENTAL_UTRACE_SDT -# define STAP_SYSCALL 0xbead -# define STAP_GUARD 0x33425250 # endif #include <sys/syscall.h> diff --git a/tapset-utrace.cxx b/tapset-utrace.cxx index e3a6fd5b..fc2fbc1d 100644 --- a/tapset-utrace.cxx +++ b/tapset-utrace.cxx @@ -1,5 +1,5 @@ // utrace tapset -// Copyright (C) 2005-2009 Red Hat Inc. +// Copyright (C) 2005-2010 Red Hat Inc. // Copyright (C) 2005-2007 Intel Corporation. // Copyright (C) 2008 James.Bottomley@HansenPartnership.com // @@ -29,7 +29,6 @@ static const string TOK_END("end"); static const string TOK_THREAD("thread"); static const string TOK_SYSCALL("syscall"); static const string TOK_RETURN("return"); -static const string TOK_LIBRARY("library"); // ------------------------------------------------------------------------ @@ -60,8 +59,8 @@ struct utrace_derived_probe: public derived_probe bool target_symbol_seen; utrace_derived_probe (systemtap_session &s, probe* p, probe_point* l, - bool hp, string &pn, bool hl, string &ln, - int64_t pd, enum utrace_derived_probe_flags f); + bool hp, string &pn, int64_t pd, + enum utrace_derived_probe_flags f); void join_group (systemtap_session& s); void emit_unprivileged_assertion (translator_output*); @@ -118,10 +117,10 @@ struct utrace_var_expanding_visitor: public var_expanding_visitor utrace_derived_probe::utrace_derived_probe (systemtap_session &s, probe* p, probe_point* l, - bool hp, string &pn, bool hl, string &ln, - int64_t pd, enum utrace_derived_probe_flags f): + bool hp, string &pn, int64_t pd, + enum utrace_derived_probe_flags f): derived_probe (p, new probe_point (*l) /* .components soon rewritten */ ), - has_path(hp), path(pn), has_library(hl), library(ln), pid(pd), flags(f), + has_path(hp), path(pn), pid(pd), flags(f), target_symbol_seen(false) { if (s.kernel_config["CONFIG_UTRACE"] != string("y")) @@ -602,11 +601,9 @@ struct utrace_builder: public derived_probe_builder vector<derived_probe *> & finished_results) { string path; - string lib; int64_t pid; bool has_path = get_param (parameters, TOK_PROCESS, path); - bool has_lib = get_param (parameters, TOK_LIBRARY, lib); bool has_pid = get_param (parameters, TOK_PROCESS, pid); enum utrace_derived_probe_flags flags = UDPF_NONE; @@ -652,11 +649,9 @@ struct utrace_builder: public derived_probe_builder // XXX: could we use /proc/$pid/exe in unwindsym_modules and elsewhere? } - if (has_lib) - lib = find_executable (lib, "LD_LIBRARY_PATH"); finished_results.push_back(new utrace_derived_probe(sess, base, location, - has_path, path, has_lib, lib, pid, + has_path, path, pid, flags)); } @@ -755,27 +750,7 @@ utrace_derived_probe_group::emit_probe_decl (systemtap_session& s, break; } s.op->line() << " .engine_attached=0,"; - - if (p->sdt_semaphore_addr != 0) - s.op->line() << " .sdt_sem_offset=(unsigned long)0x" - << hex << p->sdt_semaphore_addr << dec << "ULL,"; - s.op->line() << " .sdt_sem_address=0,"; - s.op->line() << " .tsk=0,"; s.op->line() << " },"; - - if (p->has_library && p->sdt_semaphore_addr != 0) - { - s.op->newline() << "{"; - s.op->line() << " .tgt={"; - s.op->line() << " .procname=\"" << p->path << "\","; - s.op->line() << " .mmap_callback=&stap_utrace_mmap_found,"; - s.op->line() << " },"; - s.op->line() << " .pathname=\"" << p->library << "\","; - s.op->line() << " .sdt_sem_offset=(unsigned long)0x" - << hex << p->sdt_semaphore_addr << dec << "ULL,"; - s.op->line() << " .sdt_sem_address=0,"; - s.op->line() << " },"; - } } @@ -809,12 +784,6 @@ utrace_derived_probe_group::emit_module_decls (systemtap_session& s) s.op->newline() << "enum utrace_derived_probe_flags flags;"; s.op->newline() << "struct utrace_engine_ops ops;"; s.op->newline() << "unsigned long events;"; - s.op->newline() << "struct task_struct *tsk;"; - s.op->newline() << "unsigned long sdt_sem_offset;"; - // FIXME: if this probe is attached to more than 1 task, having 1 - // address here won't work - s.op->newline() << "unsigned long sdt_sem_address;"; - s.op->newline(0) << "const char *pathname;"; s.op->newline(-1) << "};"; @@ -941,24 +910,6 @@ utrace_derived_probe_group::emit_module_decls (systemtap_session& s) s.op->newline() << "break;"; s.op->indent(-1); s.op->newline(-1) << "}"; - - s.op->newline() << "if (p->sdt_sem_offset && p->sdt_sem_address == 0) {"; - s.op->indent(1); - // If the probe is in the executable itself, the offset *is* the address. - s.op->newline() << "p->sdt_sem_address = p->sdt_sem_offset;"; - s.op->newline(-1) << "}"; - - // Before writing to the semaphore, we need to check for VM_WRITE access. - s.op->newline() << "if (p->sdt_sem_address) {"; - s.op->newline(1) << "size_t sdt_semaphore;"; - // XXX p could get registered to more than one task! - s.op->newline() << "p->tsk = tsk;"; - - s.op->newline() << "if (get_user (sdt_semaphore, (unsigned short __user *) p->sdt_sem_address) == 0) {"; - s.op->newline(1) << "sdt_semaphore ++;"; - s.op->newline() << "put_user (sdt_semaphore, (unsigned short __user *) p->sdt_sem_address);"; - s.op->newline(-1) << "}"; - s.op->newline(-1) << "}"; s.op->newline(-1) << "}"; // Since this engine could be attached to multiple threads, don't @@ -1022,40 +973,6 @@ utrace_derived_probe_group::emit_module_decls (systemtap_session& s) s.op->newline() << "return rc;"; s.op->newline(-1) << "}"; - // The task_finder_mmap_callback - s.op->newline() << "static int stap_utrace_mmap_found (struct stap_task_finder_target *tgt, struct task_struct *tsk, char *path, unsigned long addr, unsigned long length, unsigned long offset, unsigned long vm_flags) {"; - s.op->newline(1) << "struct stap_utrace_probe *p = container_of(tgt, struct stap_utrace_probe, tgt);"; - s.op->newline() << "int rc = 0;"; - // the shared library we're interested in - s.op->newline() << "if (path == NULL || strcmp (path, p->pathname)) return 0;"; - s.op->newline() << "if (p->sdt_sem_address == 0) {"; - s.op->indent(1); - // If the probe is in the executable itself, the offset *is* the - // address. - s.op->newline() << "if (vm_flags & VM_EXECUTABLE) {"; - s.op->indent(1); - s.op->newline() << "p->sdt_sem_address = addr + p->sdt_sem_offset;"; - s.op->newline(-1) << "}"; - // If the probe is in a .so, we have to calculate the address. - s.op->newline() << "else {"; - s.op->indent(1); - s.op->newline() << "p->sdt_sem_address = (addr - offset) + p->sdt_sem_offset;"; - s.op->newline(-1) << "}"; - s.op->newline(-1) << "}"; - - s.op->newline() << "if (p->sdt_sem_address && (vm_flags & VM_WRITE)) {"; - s.op->newline(1) << "unsigned short sdt_semaphore = 0;"; // NB: fixed size - s.op->newline() << "if (get_user (sdt_semaphore, (unsigned short __user *) p->sdt_sem_address) == 0) {"; - s.op->newline(1) << "sdt_semaphore ++;"; - s.op->newline() << "#ifdef DEBUG_UTRACE"; - s.op->newline() << "_stp_dbug (__FUNCTION__,__LINE__, \"+semaphore %#x @ %#lx\\n\", sdt_semaphore, p->sdt_sem_address);"; - s.op->newline() << "#endif"; - s.op->newline() << "put_user (sdt_semaphore, (unsigned short __user *) p->sdt_sem_address);"; - s.op->newline(-1) << "}"; - s.op->newline(-1) << "}"; - s.op->newline() << "return 0;"; - s.op->newline(-1) << "}"; - s.op->newline() << "static struct stap_utrace_probe stap_utrace_probes[] = {"; s.op->indent(1); @@ -1126,18 +1043,8 @@ utrace_derived_probe_group::emit_module_exit (systemtap_session& s) s.op->newline() << "if (p->engine_attached) {"; s.op->newline(1) << "stap_utrace_detach_ops(&p->ops);"; - // Before writing to the semaphore, we need to check for VM_WRITE access. - s.op->newline() << "if (p->sdt_sem_address) {"; - s.op->newline(1) << "size_t sdt_semaphore;"; - // XXX p could get registered to more than one task! - s.op->newline() << "if (get_user (sdt_semaphore, (unsigned short __user *) p->sdt_sem_address) == 0) {"; - s.op->newline(1) << "sdt_semaphore --;"; - s.op->newline() << "put_user (sdt_semaphore, (unsigned short __user *) p->sdt_sem_address);"; - s.op->newline(-1) << "}"; s.op->newline(-1) << "}"; s.op->newline(-1) << "}"; - - s.op->newline(-1) << "}"; } @@ -1166,8 +1073,6 @@ register_tapset_utrace(systemtap_session& s) ->bind(builder); roots[i]->bind(TOK_SYSCALL)->bind(TOK_RETURN) ->bind(builder); - roots[i]->bind_str(TOK_LIBRARY)->bind(TOK_SYSCALL) - ->bind(builder); } } diff --git a/tapsets.cxx b/tapsets.cxx index bac47761..f0859b21 100644 --- a/tapsets.cxx +++ b/tapsets.cxx @@ -1,5 +1,5 @@ // tapset resolution -// Copyright (C) 2005-2009 Red Hat Inc. +// Copyright (C) 2005-2010 Red Hat Inc. // Copyright (C) 2005-2007 Intel Corporation. // Copyright (C) 2008 James.Bottomley@HansenPartnership.com // @@ -3579,9 +3579,9 @@ dwarf_derived_probe_group::emit_module_exit (systemtap_session& s) struct sdt_var_expanding_visitor: public var_expanding_visitor { sdt_var_expanding_visitor(string & process_name, string & probe_name, - int arg_count, bool have_reg_args, bool utrace_probe): + int arg_count, bool have_reg_args): process_name (process_name), probe_name (probe_name), - have_reg_args (have_reg_args), utrace_probe (utrace_probe), + have_reg_args (have_reg_args), arg_count (arg_count) { assert(!have_reg_args || (arg_count >= 0 && arg_count <= 10)); @@ -3589,7 +3589,6 @@ struct sdt_var_expanding_visitor: public var_expanding_visitor string & process_name; string & probe_name; bool have_reg_args; - bool utrace_probe; int arg_count; void visit_target_symbol (target_symbol* e); @@ -3624,10 +3623,10 @@ sdt_var_expanding_visitor::visit_target_symbol (target_symbol *e) // First two args are hidden: 1. pointer to probe name 2. task id if (arg_count < 2) { - fc->function = utrace_probe ? "_utrace_syscall_arg" : "ulong_arg"; + fc->function = "ulong_arg"; fc->type = pe_long; fc->tok = e->tok; - literal_number* num = new literal_number(argno + (utrace_probe ? 1 : 2)); + literal_number* num = new literal_number(argno + 2); num->tok = e->tok; fc->args.push_back(num); } @@ -3638,9 +3637,9 @@ sdt_var_expanding_visitor::visit_target_symbol (target_symbol *e) binary_expression *be = new binary_expression; be->tok = e->tok; functioncall *get_arg1 = new functioncall; - get_arg1->function = utrace_probe ? "_utrace_syscall_arg" : "pointer_arg"; + get_arg1->function = "pointer_arg"; get_arg1->tok = e->tok; - literal_number* num = new literal_number((utrace_probe ? 2 : 3)); + literal_number* num = new literal_number(3); num->tok = e->tok; get_arg1->args.push_back(num); @@ -3687,7 +3686,6 @@ private: { uprobe_type = 0x31425250, // "PRB1" kprobe_type = 0x32425250, // "PRB2" - utrace_type = 0x33425250, // "PRB3" } probe_type; probe * base_probe; @@ -3749,9 +3747,6 @@ sdt_query::handle_query_module() case kprobe_type: clog << "kprobe" << endl; break; - case utrace_type: - clog << "utrace" << endl; - break; } } probe *new_base = new probe(*base_probe); @@ -3760,7 +3755,7 @@ sdt_query::handle_query_module() new_base->body = deep_copy_visitor::deep_copy(base_probe->body); bool have_reg_args = false; - if (probe_type == kprobe_type || probe_type == utrace_type) + if (probe_type == kprobe_type) { convert_probe(new_base); have_reg_args = true; @@ -3768,13 +3763,12 @@ sdt_query::handle_query_module() // Expand the local variables in the probe body sdt_var_expanding_visitor svv (module_val, probe_name, - probe_arg, have_reg_args, - probe_type == utrace_type); + probe_arg, have_reg_args); svv.replace (new_base->body); unsigned i = results.size(); - if (probe_type == kprobe_type || probe_type == utrace_type) + if (probe_type == kprobe_type) derive_probes(sess, new_base, results); else @@ -3889,8 +3883,7 @@ sdt_query::get_next_probe() } *pbe; __uint32_t *type = (__uint32_t*) ((char*)pdata->d_buf + probe_scn_offset); probe_type = (enum probe_types)*type; - if (probe_type != uprobe_type && probe_type != kprobe_type - && probe_type != utrace_type) + if (probe_type != uprobe_type && probe_type != kprobe_type) { // Unless this is a mangled .probes section, this happens // because the name of the probe comes first, followed by @@ -3963,28 +3956,7 @@ sdt_query::convert_probe (probe *base) } #endif - if (probe_type == utrace_type) - { - // Generate: if ($syscall != 0xbead) next; - if_statement *issc = new if_statement; - issc->thenblock = new next_statement; - issc->elseblock = NULL; - issc->tok = b->tok; - comparison *besc = new comparison; - besc->op = "!="; - besc->tok = b->tok; - functioncall* n = new functioncall; - n->tok = b->tok; - n->function = "_utrace_syscall_nr"; - n->referent = 0; - besc->left = n; - literal_number* fake_syscall = new literal_number(0xbead); - fake_syscall->tok = b->tok; - besc->right = fake_syscall; - issc->condition = besc; - b->statements.push_back(issc); - } - else if (probe_type == kprobe_type) + if (probe_type == kprobe_type) { // Generate: if (arg2 != kprobe_type) next; if_statement *istid = new if_statement; @@ -4012,9 +3984,9 @@ sdt_query::convert_probe (probe *base) // Generate: if (arg1 != mark("label")) next; functioncall *fc = new functioncall; - fc->function = (probe_type == utrace_type) ? "_utrace_syscall_arg" : "ulong_arg"; + fc->function = "ulong_arg"; fc->tok = b->tok; - literal_number* num = new literal_number((probe_type == utrace_type) ? 0 : 1); + literal_number* num = new literal_number(1); num->tok = b->tok; fc->args.push_back(num); @@ -4065,14 +4037,6 @@ sdt_query::convert_location (probe *base, probe_point *location) location->components[i]->arg = new literal_string("*getegid*"); break; - case utrace_type: - if (sess.verbose > 3) - clog << "probe_type == utrace_type" << endl; - // process("executable").syscall - location->components[i]->functor = "syscall"; - location->components[i]->arg = NULL; - break; - default: if (sess.verbose > 3) clog << "probe_type == use_uprobe_no_dwarf, use label name: " @@ -4802,7 +4766,7 @@ uprobe_derived_probe_group::emit_module_decls (systemtap_session& s) s.op->newline() << "if (likely(sups->tfi != tfi)) continue;"; // skip probes with an address beyond this map event; should not // happen unless a shlib/exec got mmapped in weirdly piecemeal - s.op->newline() << "if (likely(sups->address >= length)) continue;"; + s.op->newline() << "if (likely(sups->address >= length)) continue;"; // Found a uprobe_spec for this stap_uprobe_tf. Need to lock the // stap_uprobes[] array to allocate a free spot, but then we can @@ -4846,7 +4810,16 @@ uprobe_derived_probe_group::emit_module_decls (systemtap_session& s) s.op->newline() << "sdt_sem_address[spec_index] = relocation + sups->sdt_sem_offset;"; s.op->newline() << "sdt_sem_tid[spec_index] = tsk->tgid;"; s.op->newline(-1) << "}"; - // If the probe is in a .so, we have to calculate the address. + // If the probe is in a .so, we have to calculate the address + // when the initial mmap maps the entire solib, e.g. + // 7f089885a000-7f089885b000 rw-p- libtcl.so + // A subsequent mmap maps in the writeable segment where the + // semaphore control variable lives, which is when the variable is set. + // 7f089850d000-7f0898647000 r-xp- libtcl.so + // 7f0898647000-7f0898846000 ---p libtcl.so + // 7f0898846000-7f089885b000 rw-p- libtcl.so + // If the task changes, then recalculate the address. + s.op->newline() << "else {"; s.op->indent(1); s.op->newline() << "sdt_sem_address[spec_index] = (relocation - offset) + sups->sdt_sem_offset;"; diff --git a/testsuite/systemtap.apps/postgres.exp b/testsuite/systemtap.apps/postgres.exp index b7f522a1..9d3c18c3 100644 --- a/testsuite/systemtap.apps/postgres.exp +++ b/testsuite/systemtap.apps/postgres.exp @@ -122,14 +122,7 @@ cd postgresql-8.3.6/ mkdir bld;cd bld ../configure --enable-dtrace --prefix=$postgresdir # sed -i -e 's/ifeq (\$(PORTNAME), solaris)/ifeq (\$(enable_dtrace), yes)/' src/backend/Makefile -sed -i -e 's/^CFLAGS = -O2.*\$/& -g -DEXPERIMENTAL_UTRACE_SDT/' src/Makefile.global -make -make install -run_tests utrace - -sed -i -e 's/UTRACE/KPROBE/' src/Makefile.global -(cd src/backend/utils/ - make clean) +sed -i -e 's/^CFLAGS = -O2.*\$/& -g -DEXPERIMENTAL_KPROBE_SDT/' src/Makefile.global make make install run_tests kprobe diff --git a/testsuite/systemtap.base/sdt.exp b/testsuite/systemtap.base/sdt.exp index ea025391..8a77cc06 100644 --- a/testsuite/systemtap.base/sdt.exp +++ b/testsuite/systemtap.base/sdt.exp @@ -12,8 +12,8 @@ set ::result_string {1 set extra_flags {{""} {additional_flags=-std=gnu89} {additional_flags=-ansi} {additional_flags=-pedantic} {additional_flags=-ansi additional_flags=-pedantic} {additional_flags=-O2} {additional_flags="-O3"}} -set pbtype_flags {{""} {additional_flags=-DEXPERIMENTAL_UTRACE_SDT} {additional_flags=-DEXPERIMENTAL_KPROBE_SDT}} -set pbtype_mssgs {{uprobe} {utrace} {kprobe}} +set pbtype_flags {{""} {additional_flags=-DEXPERIMENTAL_KPROBE_SDT}} +set pbtype_mssgs {{uprobe} {kprobe}} # Iterate pbtype_flags for {set p 0} {$p < [llength $pbtype_flags]} {incr p} { diff --git a/testsuite/systemtap.base/sdt_misc.exp b/testsuite/systemtap.base/sdt_misc.exp index 062181a5..8a0cdea2 100644 --- a/testsuite/systemtap.base/sdt_misc.exp +++ b/testsuite/systemtap.base/sdt_misc.exp @@ -136,8 +136,8 @@ if {[installtest_p]} { set sdtdir $srcdir/../includes } -set pbtype_flags {{""} {additional_flags=-O additional_flags=-DEXPERIMENTAL_UTRACE_SDT} {additional_flags=-O additional_flags=-DEXPERIMENTAL_KPROBE_SDT}} -set pbtype_mssgs {{uprobe} {utrace} {kprobe}} +set pbtype_flags {{""} {additional_flags=-O additional_flags=-DEXPERIMENTAL_KPROBE_SDT}} +set pbtype_mssgs {{uprobe} {kprobe}} # Iterate pbtype_flags for {set i 0} {$i < [llength $pbtype_flags]} {incr i} { |