summaryrefslogtreecommitdiffstats
path: root/tapsets.cxx
diff options
context:
space:
mode:
authorStan Cox <scox@redhat.com>2009-09-16 21:05:00 -0400
committerStan Cox <scox@redhat.com>2009-09-16 21:05:00 -0400
commit6846cfc8a5cdb24fccb19037b27a180d2300ee09 (patch)
tree9dbcddce5f4410d96b98ec5beb757e74c901e74c /tapsets.cxx
parent9f7d5236c8fb1fd84636656416e1dad531e9586d (diff)
downloadsystemtap-steved-6846cfc8a5cdb24fccb19037b27a180d2300ee09.tar.gz
systemtap-steved-6846cfc8a5cdb24fccb19037b27a180d2300ee09.tar.xz
systemtap-steved-6846cfc8a5cdb24fccb19037b27a180d2300ee09.zip
* sdt.h (STAP_SEMAPHORE): New. Add guard to utrace probe points.
* itrace.h (__access_process_vm): Moved from here... * runtime/access_process_vm.h: New. ...to here. * translate.cxx (translate_pass): Include access_process_vm.h * session.h (sdt_semaphore_addr): New. * tapsets.cxx (sdt_query::record_semaphore): New. Record sdt_semaphore_addr. (uprobe_derived_probe_group::emit_module_decls): Allow for uprobe guard variable to be set and unset. (uprobe_derived_probe_group::emit_module_decls): Likewise. (uprobe_derived_probe_group::emit_module_exit): Likewise. * tapset-utrace.cxx (utrace_derived_probe_group::emit_probe_decl): Likewise. (utrace_derived_probe_group::emit_module_decls): Likewise. (utrace_derived_probe_group::emit_module_exit): Likewise.
Diffstat (limited to 'tapsets.cxx')
-rw-r--r--tapsets.cxx86
1 files changed, 81 insertions, 5 deletions
diff --git a/tapsets.cxx b/tapsets.cxx
index 977a92fa..00927b2d 100644
--- a/tapsets.cxx
+++ b/tapsets.cxx
@@ -3458,6 +3458,7 @@ private:
probe * base_probe;
probe_point * base_loc;
+ literal_map_t const & params;
vector<derived_probe *> & results;
string mark_name;
@@ -3473,6 +3474,7 @@ private:
bool get_next_probe();
void convert_probe(probe *base);
+ void record_semaphore(vector<derived_probe *> & results);
void convert_location(probe *base, probe_point *location);
};
@@ -3481,7 +3483,7 @@ sdt_query::sdt_query(probe * base_probe, probe_point * base_loc,
dwflpp & dw, literal_map_t const & params,
vector<derived_probe *> & results):
base_query(dw, params), base_probe(base_probe),
- base_loc(base_loc), results(results)
+ base_loc(base_loc), params(params), results(results)
{
assert(get_string_param(params, TOK_MARK, mark_name));
}
@@ -3523,7 +3525,11 @@ sdt_query::handle_query_module()
unsigned i = results.size();
if (probe_type == kprobe_type || probe_type == utrace_type)
- derive_probes(sess, new_base, results);
+ {
+ derive_probes(sess, new_base, results);
+ record_semaphore(results);
+ }
+
else
{
literal_map_t params;
@@ -3536,6 +3542,7 @@ sdt_query::handle_query_module()
dwarf_query q(new_base, new_location, dw, params, results);
q.has_mark = true; // enables mid-statement probing
dw.iterate_over_modules(&query_module, &q);
+ record_semaphore(results);
}
if (sess.listing_mode)
@@ -3667,6 +3674,28 @@ sdt_query::get_next_probe()
void
+sdt_query::record_semaphore (vector<derived_probe *> & results)
+{
+ int sym_count = dwfl_module_getsymtab(dw.module);
+ assert (sym_count >= 0);
+ for (int i = 0; i < sym_count; i++)
+ {
+ GElf_Sym sym;
+ GElf_Word shndxp;
+ char *sym_str = (char*)dwfl_module_getsym (dw.module, i, &sym, &shndxp);
+ if (strcmp(sym_str, string(probe_name + "_semaphore").c_str()) == 0)
+ {
+ string process_name;
+ derived_probe_builder::get_param(params, TOK_PROCESS, process_name);
+ for (unsigned int i = 0; i < results.size(); ++i)
+ sess.sdt_semaphore_addr.insert(make_pair(sym.st_value, results[i]));
+ break;
+ }
+ }
+}
+
+
+void
sdt_query::convert_probe (probe *base)
{
block *b = new block;
@@ -4392,6 +4421,8 @@ uprobe_derived_probe_group::emit_module_decls (systemtap_session& s)
s.op->newline() << "unsigned long address;";
s.op->newline() << "const char *pp;";
s.op->newline() << "void (*ph) (struct context*);";
+ s.op->newline() << "unsigned long sdt_sem_address;";
+ s.op->newline() << "struct task_struct *tsk;";
s.op->newline() << "unsigned return_p:1;";
s.op->newline(-1) << "} stap_uprobe_specs [] = {";
s.op->indent(1);
@@ -4405,6 +4436,21 @@ uprobe_derived_probe_group::emit_module_decls (systemtap_session& s)
s.op->line() << " .address=(unsigned long)0x" << hex << p->addr << dec << "ULL,";
s.op->line() << " .pp=" << lex_cast_qstring (*p->sole_location()) << ",";
s.op->line() << " .ph=&" << p->name << ",";
+ map<Dwarf_Addr, derived_probe*>::iterator its;
+ if (s.sdt_semaphore_addr.empty())
+ s.op->line() << " .sdt_sem_address=(unsigned long)0x0,";
+ else
+ for (its = s.sdt_semaphore_addr.begin();
+ its != s.sdt_semaphore_addr.end();
+ its++)
+ {
+ if (p->module == ((struct uprobe_derived_probe*)(its->second))->module
+ && p->addr == ((struct uprobe_derived_probe*)(its->second))->addr)
+ {
+ s.op->line() << " .sdt_sem_address=(unsigned long)0x" << hex << its->first << dec << "ULL,";
+ break;
+ }
+ }
if (p->has_return) s.op->line() << " .return_p=1,";
s.op->line() << " },";
}
@@ -4478,7 +4524,7 @@ uprobe_derived_probe_group::emit_module_decls (systemtap_session& s)
s.op->newline() << "for (spec_index=0; spec_index<sizeof(stap_uprobe_specs)/sizeof(stap_uprobe_specs[0]); spec_index++) {";
s.op->newline(1) << "int handled_p = 0;";
s.op->newline() << "int slotted_p = 0;";
- s.op->newline() << "const struct stap_uprobe_spec *sups = &stap_uprobe_specs [spec_index];";
+ s.op->newline() << "struct stap_uprobe_spec *sups = (struct stap_uprobe_spec*) &stap_uprobe_specs [spec_index];";
s.op->newline() << "int rc = 0;";
s.op->newline() << "int i;";
@@ -4558,6 +4604,16 @@ uprobe_derived_probe_group::emit_module_decls (systemtap_session& s)
s.op->newline(-1) << "}";
s.op->newline(-1) << "}";
+ //----------
+ s.op->newline() << "if (sups->sdt_sem_address != 0) {";
+ s.op->newline(1) << "size_t sdt_semaphore;";
+ s.op->newline() << "sups->tsk = tsk;";
+ s.op->newline() << "__access_process_vm (tsk, relocation + sups->sdt_sem_address, &sdt_semaphore, sizeof (sdt_semaphore), 0);";
+ s.op->newline() << "sdt_semaphore += 1;";
+ s.op->newline() << "__access_process_vm (tsk, relocation + sups->sdt_sem_address, &sdt_semaphore, sizeof (sdt_semaphore), 1);";
+ s.op->newline(-1) << "}";
+ //----------
+
// close iteration over stap_uprobe_spec[]
s.op->newline(-1) << "}";
@@ -4580,9 +4636,9 @@ uprobe_derived_probe_group::emit_module_decls (systemtap_session& s)
s.op->newline() << "for (i=0; i<MAXUPROBES; i++) {"; // XXX: slow linear search
s.op->newline(1) << "struct stap_uprobe *sup = & stap_uprobes[i];";
- s.op->newline() << "const struct stap_uprobe_spec *sups;";
+ s.op->newline() << "struct stap_uprobe_spec *sups;";
s.op->newline() << "if (sup->spec_index < 0) continue;"; // skip free uprobes slot
- s.op->newline() << "sups = & stap_uprobe_specs[sup->spec_index];";
+ s.op->newline() << "sups = (struct stap_uprobe_spec*) & stap_uprobe_specs[sup->spec_index];";
s.op->newline() << "mutex_lock (& stap_uprobes_lock);";
@@ -4642,6 +4698,16 @@ uprobe_derived_probe_group::emit_module_decls (systemtap_session& s)
s.op->newline() << "mutex_unlock (& stap_uprobes_lock);";
+ //----------
+ s.op->newline() << "if (sups->sdt_sem_address != 0) {";
+ s.op->newline(1) << "size_t sdt_semaphore;";
+ s.op->newline() << "sups->tsk = tsk;";
+ s.op->newline() << "__access_process_vm (tsk, sups->sdt_sem_address, &sdt_semaphore, sizeof (sdt_semaphore), 0);";
+ s.op->newline() << "sdt_semaphore += 1;";
+ s.op->newline() << "__access_process_vm (tsk, sups->sdt_sem_address, &sdt_semaphore, sizeof (sdt_semaphore), 1);";
+ s.op->newline(-1) << "}";
+ //----------
+
// close iteration over stap_uprobes[]
s.op->newline(-1) << "}";
@@ -4765,6 +4831,16 @@ uprobe_derived_probe_group::emit_module_exit (systemtap_session& s)
s.op->newline() << "const struct stap_uprobe_spec *sups = &stap_uprobe_specs [sup->spec_index];";
s.op->newline() << "if (sup->spec_index < 0) continue;"; // free slot
+ //----------
+ s.op->newline() << "if (sups->sdt_sem_address != 0) {";
+ s.op->newline(1) << "size_t sdt_semaphore;";
+ s.op->newline() << "__access_process_vm (sups->tsk, sups->sdt_sem_address, &sdt_semaphore, sizeof (sdt_semaphore), 0);";
+ s.op->newline() << "sdt_semaphore -= 1;";
+ s.op->newline() << "__access_process_vm (sups->tsk, sups->sdt_sem_address, &sdt_semaphore, sizeof (sdt_semaphore), 1);";
+ s.op->newline(-1) << "}";
+ //----------
+
+
s.op->newline() << "if (sups->return_p) {";
s.op->newline(1) << "#ifdef DEBUG_UPROBES";
s.op->newline() << "_stp_dbug (__FUNCTION__,__LINE__, \"-uretprobe spec %d index %d pid %d addr %p\\n\", sup->spec_index, j, sup->up.pid, (void*) sup->up.vaddr);";