summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJosh Stone <jistone@redhat.com>2009-06-09 19:58:15 -0700
committerJosh Stone <jistone@redhat.com>2009-06-09 20:08:12 -0700
commit67146982d334acdb25f43da2a74c02fcabc3c45d (patch)
tree61198a6a941aed9efdd8f9878b71fd2683c1447a
parentb608bb8322085893877078d76e3e50f7d9918c5a (diff)
downloadsystemtap-steved-67146982d334acdb25f43da2a74c02fcabc3c45d.tar.gz
systemtap-steved-67146982d334acdb25f43da2a74c02fcabc3c45d.tar.xz
systemtap-steved-67146982d334acdb25f43da2a74c02fcabc3c45d.zip
Fix condition propagation across aliases
When an instance of an alias has a condition, that condition gets propagated to each of the locations that the alias defines. However, the copy of the location list was not a deep copy, and so all other instances of the alias would also incorrectly receive the condition. This patch makes the location list copy a little deeper, and adds a test case which demonstrates the issue.
-rw-r--r--elaborate.cxx14
-rw-r--r--testsuite/systemtap.base/alias-condition.exp5
-rw-r--r--testsuite/systemtap.base/alias-condition.stp26
3 files changed, 40 insertions, 5 deletions
diff --git a/elaborate.cxx b/elaborate.cxx
index 7c4a5fca..30e9a775 100644
--- a/elaborate.cxx
+++ b/elaborate.cxx
@@ -488,11 +488,15 @@ alias_expansion_builder
alias_derived_probe * n = new alias_derived_probe (use, location /* soon overwritten */, this->alias);
n->body = new block();
- // The new probe gets the location list of the alias (with incoming condition joined)
- n->locations = alias->locations;
- for (unsigned i=0; i<n->locations.size(); i++)
- n->locations[i]->condition = add_condition (n->locations[i]->condition,
- location->condition);
+ // The new probe gets a deep copy of the location list of
+ // the alias (with incoming condition joined)
+ n->locations.clear();
+ for (unsigned i=0; i<alias->locations.size(); i++)
+ {
+ probe_point *pp = new probe_point(*alias->locations[i]);
+ pp->condition = add_condition (pp->condition, location->condition);
+ n->locations.push_back(pp);
+ }
// the token location of the alias,
n->tok = location->tok;
diff --git a/testsuite/systemtap.base/alias-condition.exp b/testsuite/systemtap.base/alias-condition.exp
new file mode 100644
index 00000000..58438340
--- /dev/null
+++ b/testsuite/systemtap.base/alias-condition.exp
@@ -0,0 +1,5 @@
+# Check that conditions are copied correctly across aliases
+
+set test "alias-condition"
+
+stap_run $srcdir/$subdir/$test.stp no_load $all_pass_string
diff --git a/testsuite/systemtap.base/alias-condition.stp b/testsuite/systemtap.base/alias-condition.stp
new file mode 100644
index 00000000..89708886
--- /dev/null
+++ b/testsuite/systemtap.base/alias-condition.stp
@@ -0,0 +1,26 @@
+/*
+ * alias-condition.stp
+ *
+ * Check that conditions are copied correctly across aliases
+ */
+
+/* x should be incremented exactly once */
+global x = 0
+probe foo = begin { }
+probe foo if (x < 0), foo { ++x }
+
+probe begin(1)
+{
+ println("systemtap starting probe")
+ exit()
+}
+
+probe end
+{
+ println("systemtap ending probe")
+ if ( x != 1 ) {
+ println("systemtap test failure")
+ } else {
+ println("systemtap test success")
+ }
+}