You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@mesos.apache.org by bm...@apache.org on 2015/09/15 02:26:48 UTC

[1/7] mesos git commit: Removed 'using namespace process' in perf event isolator.

Repository: mesos
Updated Branches:
  refs/heads/master 1c10fdbfa -> ddaa556dd


Removed 'using namespace process' in perf event isolator.

Review: https://reviews.apache.org/r/38377


Project: http://git-wip-us.apache.org/repos/asf/mesos/repo
Commit: http://git-wip-us.apache.org/repos/asf/mesos/commit/3949de25
Tree: http://git-wip-us.apache.org/repos/asf/mesos/tree/3949de25
Diff: http://git-wip-us.apache.org/repos/asf/mesos/diff/3949de25

Branch: refs/heads/master
Commit: 3949de25248d0c0f737b55f9477c9b470f2ff748
Parents: 3ff3f08
Author: Benjamin Mahler <be...@gmail.com>
Authored: Mon Sep 14 12:51:57 2015 -0700
Committer: Benjamin Mahler <be...@gmail.com>
Committed: Mon Sep 14 16:56:19 2015 -0700

----------------------------------------------------------------------
 .../containerizer/isolators/cgroups/perf_event.cpp    | 14 +++++++++-----
 1 file changed, 9 insertions(+), 5 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/mesos/blob/3949de25/src/slave/containerizer/isolators/cgroups/perf_event.cpp
----------------------------------------------------------------------
diff --git a/src/slave/containerizer/isolators/cgroups/perf_event.cpp b/src/slave/containerizer/isolators/cgroups/perf_event.cpp
index 7dc8b7a..a362182 100644
--- a/src/slave/containerizer/isolators/cgroups/perf_event.cpp
+++ b/src/slave/containerizer/isolators/cgroups/perf_event.cpp
@@ -46,17 +46,21 @@
 
 #include "slave/containerizer/isolators/cgroups/perf_event.hpp"
 
-using namespace process;
+using mesos::slave::ContainerLimitation;
+using mesos::slave::ContainerPrepareInfo;
+using mesos::slave::ContainerState;
+using mesos::slave::Isolator;
 
 using std::list;
 using std::set;
 using std::string;
 using std::vector;
 
-using mesos::slave::ContainerLimitation;
-using mesos::slave::ContainerPrepareInfo;
-using mesos::slave::ContainerState;
-using mesos::slave::Isolator;
+using process::Clock;
+using process::Failure;
+using process::Future;
+using process::PID;
+using process::Time;
 
 namespace mesos {
 namespace internal {


[7/7] mesos git commit: Fixed the perf event isolator to continue sampling in the presence of failures.

Posted by bm...@apache.org.
Fixed the perf event isolator to continue sampling in the presence of failures.

Review: https://reviews.apache.org/r/38382


Project: http://git-wip-us.apache.org/repos/asf/mesos/repo
Commit: http://git-wip-us.apache.org/repos/asf/mesos/commit/ddaa556d
Tree: http://git-wip-us.apache.org/repos/asf/mesos/tree/ddaa556d
Diff: http://git-wip-us.apache.org/repos/asf/mesos/diff/ddaa556d

Branch: refs/heads/master
Commit: ddaa556dde8f9937f89b9341d83b1ba1e9305ff4
Parents: 72f8452
Author: Benjamin Mahler <be...@gmail.com>
Authored: Mon Sep 14 14:45:47 2015 -0700
Committer: Benjamin Mahler <be...@gmail.com>
Committed: Mon Sep 14 17:05:29 2015 -0700

----------------------------------------------------------------------
 .../isolators/cgroups/perf_event.cpp            | 30 +++++++++-----------
 1 file changed, 14 insertions(+), 16 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/mesos/blob/ddaa556d/src/slave/containerizer/isolators/cgroups/perf_event.cpp
----------------------------------------------------------------------
diff --git a/src/slave/containerizer/isolators/cgroups/perf_event.cpp b/src/slave/containerizer/isolators/cgroups/perf_event.cpp
index f6ab8bc..03035df 100644
--- a/src/slave/containerizer/isolators/cgroups/perf_event.cpp
+++ b/src/slave/containerizer/isolators/cgroups/perf_event.cpp
@@ -383,10 +383,8 @@ void CgroupsPerfEventIsolatorProcess::sample()
     }
   }
 
-  // The timeout includes an allowance of twice the process::reap
-  // interval to ensure we see the perf process exit. If the sample
-  // is not ready after the timeout something very unexpected has
-  // occurred so we discard it and halt all sampling.
+  // The discard timeout includes an allowance of twice the
+  // reaper interval to ensure we see the perf process exit.
   Duration timeout = flags.perf_duration + process::MAX_REAP_INTERVAL() * 2;
 
   perf::sample(events, cgroups, flags.perf_duration)
@@ -407,22 +405,22 @@ void CgroupsPerfEventIsolatorProcess::_sample(
     const Future<hashmap<string, PerfStatistics>>& statistics)
 {
   if (!statistics.isReady()) {
-    // Failure can occur for many reasons but all are unexpected and
-    // indicate something is not right so we'll stop sampling.
-    LOG(ERROR) << "Failed to get perf sample, sampling will be halted: "
+    // In case the failure is transient or this is due to a timeout,
+    // we continue sampling. Note that since sampling is done on an
+    // interval, it should be ok if this is a non-transient failure.
+    LOG(ERROR) << "Failed to get perf sample: "
                << (statistics.isFailed()
                    ? statistics.failure()
                    : "discarded due to timeout");
-    return;
-  }
-
-  // Store the latest statistics, note that cgroups added in the
-  // interim will be picked up by the next sample.
-  foreachvalue (Info* info, infos) {
-    CHECK_NOTNULL(info);
+  } else {
+    // Store the latest statistics, note that cgroups added in the
+    // interim will be picked up by the next sample.
+    foreachvalue (Info* info, infos) {
+      CHECK_NOTNULL(info);
 
-    if (statistics->contains(info->cgroup)) {
-      info->statistics = statistics->get(info->cgroup).get();
+      if (statistics->contains(info->cgroup)) {
+        info->statistics = statistics->get(info->cgroup).get();
+      }
     }
   }
 


[2/7] mesos git commit: Fixed process::collect and process::await to do discard propagation.

Posted by bm...@apache.org.
Fixed process::collect and process::await to do discard propagation.

Review: https://reviews.apache.org/r/38375


Project: http://git-wip-us.apache.org/repos/asf/mesos/repo
Commit: http://git-wip-us.apache.org/repos/asf/mesos/commit/3ff3f08f
Tree: http://git-wip-us.apache.org/repos/asf/mesos/tree/3ff3f08f
Diff: http://git-wip-us.apache.org/repos/asf/mesos/diff/3ff3f08f

Branch: refs/heads/master
Commit: 3ff3f08f2dcc2a1c58ff9869a58c29029ab0c816
Parents: 1c10fdb
Author: Benjamin Mahler <be...@gmail.com>
Authored: Mon Sep 14 15:35:42 2015 -0700
Committer: Benjamin Mahler <be...@gmail.com>
Committed: Mon Sep 14 16:56:19 2015 -0700

----------------------------------------------------------------------
 3rdparty/libprocess/Makefile.am                 |   1 +
 3rdparty/libprocess/include/process/collect.hpp |  54 ++--
 3rdparty/libprocess/src/tests/CMakeLists.txt    |   1 +
 3rdparty/libprocess/src/tests/collect_tests.cpp | 246 +++++++++++++++++++
 3rdparty/libprocess/src/tests/process_tests.cpp | 188 --------------
 5 files changed, 277 insertions(+), 213 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/mesos/blob/3ff3f08f/3rdparty/libprocess/Makefile.am
----------------------------------------------------------------------
diff --git a/3rdparty/libprocess/Makefile.am b/3rdparty/libprocess/Makefile.am
index 6361ac6..064310c 100644
--- a/3rdparty/libprocess/Makefile.am
+++ b/3rdparty/libprocess/Makefile.am
@@ -137,6 +137,7 @@ endif
 check_PROGRAMS = tests benchmarks
 
 tests_SOURCES =							\
+  src/tests/collect_tests.cpp					\
   src/tests/decoder_tests.cpp					\
   src/tests/encoder_tests.cpp					\
   src/tests/future_tests.cpp					\

http://git-wip-us.apache.org/repos/asf/mesos/blob/3ff3f08f/3rdparty/libprocess/include/process/collect.hpp
----------------------------------------------------------------------
diff --git a/3rdparty/libprocess/include/process/collect.hpp b/3rdparty/libprocess/include/process/collect.hpp
index d07b686..2a8547b 100644
--- a/3rdparty/libprocess/include/process/collect.hpp
+++ b/3rdparty/libprocess/include/process/collect.hpp
@@ -93,9 +93,8 @@ public:
     // Stop this nonsense if nobody cares.
     promise->future().onDiscard(defer(this, &CollectProcess::discarded));
 
-    typename std::list<Future<T>>::const_iterator iterator;
-    for (iterator = futures.begin(); iterator != futures.end(); ++iterator) {
-      (*iterator).onAny(defer(this, &CollectProcess::waited, lambda::_1));
+    foreach (const Future<T>& future, futures) {
+      future.onAny(defer(this, &CollectProcess::waited, lambda::_1));
     }
   }
 
@@ -103,6 +102,11 @@ private:
   void discarded()
   {
     promise->discard();
+
+    foreach (Future<T> future, futures) {
+      future.discard();
+    }
+
     terminate(this);
   }
 
@@ -155,9 +159,8 @@ public:
     // Stop this nonsense if nobody cares.
     promise->future().onDiscard(defer(this, &AwaitProcess::discarded));
 
-    typename std::list<Future<T>>::const_iterator iterator;
-    for (iterator = futures.begin(); iterator != futures.end(); ++iterator) {
-      (*iterator).onAny(defer(this, &AwaitProcess::waited, lambda::_1));
+    foreach (const Future<T>& future, futures) {
+      future.onAny(defer(this, &AwaitProcess::waited, lambda::_1));
     }
   }
 
@@ -165,6 +168,11 @@ private:
   void discarded()
   {
     promise->discard();
+
+    foreach (Future<T> future, futures) {
+      future.discard();
+    }
+
     terminate(this);
   }
 
@@ -242,15 +250,13 @@ Future<std::tuple<Future<T1>, Future<T2>>> await(
     const Future<T1>& future1,
     const Future<T2>& future2)
 {
-  Owned<Promise<Nothing>> promise1(new Promise<Nothing>());
-  Owned<Promise<Nothing>> promise2(new Promise<Nothing>());
+  Future<Nothing> wrapper1 = future1
+    .then([]() { return Nothing(); });
 
-  future1.onAny([=]() { promise1->set(Nothing()); });
-  future2.onAny([=]() { promise2->set(Nothing()); });
+  Future<Nothing> wrapper2 = future2
+    .then([]() { return Nothing(); });
 
-  std::list<Future<Nothing>> futures;
-  futures.push_back(promise1->future());
-  futures.push_back(promise2->future());
+  std::list<Future<Nothing>> futures = { wrapper1, wrapper2 };
 
   return await(futures)
     .then([=]() { return std::make_tuple(future1, future2); });
@@ -263,18 +269,16 @@ Future<std::tuple<Future<T1>, Future<T2>, Future<T3>>> await(
     const Future<T2>& future2,
     const Future<T3>& future3)
 {
-  Owned<Promise<Nothing>> promise1(new Promise<Nothing>());
-  Owned<Promise<Nothing>> promise2(new Promise<Nothing>());
-  Owned<Promise<Nothing>> promise3(new Promise<Nothing>());
-
-  future1.onAny([=]() { promise1->set(Nothing()); });
-  future2.onAny([=]() { promise2->set(Nothing()); });
-  future3.onAny([=]() { promise3->set(Nothing()); });
-
-  std::list<Future<Nothing>> futures;
-  futures.push_back(promise1->future());
-  futures.push_back(promise2->future());
-  futures.push_back(promise3->future());
+  Future<Nothing> wrapper1 = future1
+    .then([]() { return Nothing(); });
+
+  Future<Nothing> wrapper2 = future2
+    .then([]() { return Nothing(); });
+
+  Future<Nothing> wrapper3 = future3
+    .then([]() { return Nothing(); });
+
+  std::list<Future<Nothing>> futures = { wrapper1, wrapper2, wrapper3 };
 
   return await(futures)
     .then([=]() { return std::make_tuple(future1, future2, future3); });

http://git-wip-us.apache.org/repos/asf/mesos/blob/3ff3f08f/3rdparty/libprocess/src/tests/CMakeLists.txt
----------------------------------------------------------------------
diff --git a/3rdparty/libprocess/src/tests/CMakeLists.txt b/3rdparty/libprocess/src/tests/CMakeLists.txt
index b61ca1e..a14b5b8 100644
--- a/3rdparty/libprocess/src/tests/CMakeLists.txt
+++ b/3rdparty/libprocess/src/tests/CMakeLists.txt
@@ -20,6 +20,7 @@ set(PROCESS_TESTS_TARGET process_tests)
 ################
 set(PROCESS_TESTS_SRC
   ${PROCESS_TESTS_SRC}
+  collect_tests.cpp
   decoder_tests.cpp
   encoder_tests.cpp
   http_tests.cpp

http://git-wip-us.apache.org/repos/asf/mesos/blob/3ff3f08f/3rdparty/libprocess/src/tests/collect_tests.cpp
----------------------------------------------------------------------
diff --git a/3rdparty/libprocess/src/tests/collect_tests.cpp b/3rdparty/libprocess/src/tests/collect_tests.cpp
new file mode 100644
index 0000000..da533af
--- /dev/null
+++ b/3rdparty/libprocess/src/tests/collect_tests.cpp
@@ -0,0 +1,246 @@
+/**
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at
+*
+*     http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License
+*/
+
+#include <process/collect.hpp>
+#include <process/gtest.hpp>
+
+#include <stout/gtest.hpp>
+
+using process::Future;
+using process::Promise;
+
+using std::list;
+
+TEST(CollectTest, Ready)
+{
+  // First ensure an empty list functions correctly.
+  list<Future<int>> empty;
+  Future<list<int>> collect = process::collect(empty);
+
+  AWAIT_READY(collect);
+  EXPECT_TRUE(collect.get().empty());
+
+  Promise<int> promise1;
+  Promise<int> promise2;
+  Promise<int> promise3;
+  Promise<int> promise4;
+
+  list<Future<int>> futures;
+  futures.push_back(promise1.future());
+  futures.push_back(promise2.future());
+  futures.push_back(promise3.future());
+  futures.push_back(promise4.future());
+
+  // Set them out-of-order.
+  promise4.set(4);
+  promise2.set(2);
+  promise1.set(1);
+  promise3.set(3);
+
+  collect = process::collect(futures);
+
+  AWAIT_ASSERT_READY(collect);
+
+  list<int> values;
+  values.push_back(1);
+  values.push_back(2);
+  values.push_back(3);
+  values.push_back(4);
+
+  // We expect them to be returned in the same order as the
+  // future list that was passed in.
+  EXPECT_EQ(values, collect.get());
+}
+
+
+TEST(CollectTest, Failure)
+{
+  Promise<int> promise1;
+  Promise<bool> promise2;
+
+  Future<std::tuple<int, bool>> collect =
+    process::collect(promise1.future(), promise2.future());
+
+  ASSERT_TRUE(collect.isPending());
+
+  promise1.set(42);
+
+  ASSERT_TRUE(collect.isPending());
+
+  promise2.set(true);
+
+  AWAIT_READY(collect);
+
+  std::tuple<int, bool> values = collect.get();
+
+  ASSERT_EQ(42, std::get<0>(values));
+  ASSERT_TRUE(std::get<1>(values));
+
+  // Collect should fail when a future fails.
+  Promise<bool> promise3;
+
+  collect = process::collect(promise1.future(), promise3.future());
+
+  ASSERT_TRUE(collect.isPending());
+
+  promise3.fail("failure");
+
+  AWAIT_FAILED(collect);
+
+  // Collect should fail when a future is discarded.
+  Promise<bool> promise4;
+
+  collect = process::collect(promise1.future(), promise4.future());
+
+  ASSERT_TRUE(collect.isPending());
+
+  promise4.discard();
+
+  AWAIT_FAILED(collect);
+}
+
+
+TEST(CollectTest, DiscardPropagation)
+{
+  Future<int> future1;
+  Future<bool> future2;
+
+  future1
+    .onDiscard([=](){ process::internal::discarded(future1); });
+  future2
+    .onDiscard([=](){ process::internal::discarded(future2); });
+
+  Future<std::tuple<int, bool>> collect = process::collect(future1, future2);
+
+  collect.discard();
+
+  AWAIT_DISCARDED(future1);
+  AWAIT_DISCARDED(future2);
+}
+
+
+TEST(AwaitTest, Success)
+{
+  // First ensure an empty list functions correctly.
+  list<Future<int>> empty;
+  Future<list<Future<int>>> future = process::await(empty);
+  AWAIT_ASSERT_READY(future);
+  EXPECT_TRUE(future.get().empty());
+
+  Promise<int> promise1;
+  Promise<int> promise2;
+  Promise<int> promise3;
+  Promise<int> promise4;
+
+  list<Future<int>> futures;
+  futures.push_back(promise1.future());
+  futures.push_back(promise2.future());
+  futures.push_back(promise3.future());
+  futures.push_back(promise4.future());
+
+  // Set them out-of-order.
+  promise4.set(4);
+  promise2.set(2);
+  promise1.set(1);
+  promise3.set(3);
+
+  future = process::await(futures);
+
+  AWAIT_ASSERT_READY(future);
+
+  EXPECT_EQ(futures.size(), future.get().size());
+
+  // We expect them to be returned in the same order as the
+  // future list that was passed in.
+  int i = 1;
+  foreach (const Future<int>& result, future.get()) {
+    ASSERT_TRUE(result.isReady());
+    ASSERT_EQ(i, result.get());
+    ++i;
+  }
+}
+
+
+TEST(AwaitTest, Failure)
+{
+  Promise<int> promise1;
+  Promise<bool> promise2;
+
+  Future<std::tuple<Future<int>, Future<bool>>> await =
+    process::await(promise1.future(), promise2.future());
+
+  ASSERT_TRUE(await.isPending());
+
+  promise1.set(42);
+
+  ASSERT_TRUE(await.isPending());
+
+  promise2.fail("failure message");
+
+  AWAIT_READY(await);
+
+  std::tuple<Future<int>, Future<bool>> futures = await.get();
+
+  ASSERT_TRUE(std::get<0>(futures).isReady());
+  ASSERT_EQ(42, std::get<0>(futures).get());
+
+  ASSERT_TRUE(std::get<1>(futures).isFailed());
+}
+
+
+TEST(AwaitTest, Discarded)
+{
+  Promise<int> promise1;
+  Promise<bool> promise2;
+
+  Future<std::tuple<Future<int>, Future<bool>>> await =
+    process::await(promise1.future(), promise2.future());
+
+  ASSERT_TRUE(await.isPending());
+
+  promise1.set(42);
+
+  ASSERT_TRUE(await.isPending());
+
+  promise2.discard();
+
+  AWAIT_READY(await);
+
+  std::tuple<Future<int>, Future<bool>> futures = await.get();
+
+  ASSERT_TRUE(std::get<0>(futures).isReady());
+  ASSERT_EQ(42, std::get<0>(futures).get());
+
+  ASSERT_TRUE(std::get<1>(futures).isDiscarded());
+}
+
+
+TEST(AwaitTest, DiscardPropagation)
+{
+  Future<int> future1;
+  Future<bool> future2;
+
+  future1
+    .onDiscard([=](){ process::internal::discarded(future1); });
+  future2
+    .onDiscard([=](){ process::internal::discarded(future2); });
+
+  Future<std::tuple<Future<int>, Future<bool>>> await =
+    process::await(future1, future2);
+
+  await.discard();
+
+  AWAIT_DISCARDED(future1);
+  AWAIT_DISCARDED(future2);
+}

http://git-wip-us.apache.org/repos/asf/mesos/blob/3ff3f08f/3rdparty/libprocess/src/tests/process_tests.cpp
----------------------------------------------------------------------
diff --git a/3rdparty/libprocess/src/tests/process_tests.cpp b/3rdparty/libprocess/src/tests/process_tests.cpp
index 435663b..1023500 100644
--- a/3rdparty/libprocess/src/tests/process_tests.cpp
+++ b/3rdparty/libprocess/src/tests/process_tests.cpp
@@ -27,7 +27,6 @@
 #include <vector>
 
 #include <process/async.hpp>
-#include <process/collect.hpp>
 #include <process/clock.hpp>
 #include <process/defer.hpp>
 #include <process/delay.hpp>
@@ -1165,193 +1164,6 @@ TEST(ProcessTest, Select)
 }
 
 
-TEST(ProcessTest, Collect1)
-{
-  ASSERT_TRUE(GTEST_IS_THREADSAFE);
-
-  // First ensure an empty list functions correctly.
-  std::list<Future<int>> empty;
-  Future<std::list<int>> future = collect(empty);
-
-  AWAIT_READY(future);
-  EXPECT_TRUE(future.get().empty());
-
-  Promise<int> promise1;
-  Promise<int> promise2;
-  Promise<int> promise3;
-  Promise<int> promise4;
-
-  std::list<Future<int>> futures;
-  futures.push_back(promise1.future());
-  futures.push_back(promise2.future());
-  futures.push_back(promise3.future());
-  futures.push_back(promise4.future());
-
-  // Set them out-of-order.
-  promise4.set(4);
-  promise2.set(2);
-  promise1.set(1);
-  promise3.set(3);
-
-  future = collect(futures);
-
-  AWAIT_ASSERT_READY(future);
-
-  std::list<int> values;
-  values.push_back(1);
-  values.push_back(2);
-  values.push_back(3);
-  values.push_back(4);
-
-  // We expect them to be returned in the same order as the
-  // future list that was passed in.
-  EXPECT_EQ(values, future.get());
-}
-
-
-TEST(ProcessTest, Collect2)
-{
-  Promise<int> promise1;
-  Promise<bool> promise2;
-
-  Future<std::tuple<int, bool>> future =
-    collect(promise1.future(), promise2.future());
-
-  ASSERT_TRUE(future.isPending());
-
-  promise1.set(42);
-
-  ASSERT_TRUE(future.isPending());
-
-  promise2.set(true);
-
-  AWAIT_READY(future);
-
-  std::tuple<int, bool> values = future.get();
-
-  ASSERT_EQ(42, std::get<0>(values));
-  ASSERT_TRUE(std::get<1>(values));
-
-  // Collect should fail when a future fails.
-  Promise<bool> promise3;
-
-  future = collect(promise1.future(), promise3.future());
-
-  ASSERT_TRUE(future.isPending());
-
-  promise3.fail("failure");
-
-  AWAIT_FAILED(future);
-
-  // Collect should fail when a future is discarded.
-  Promise<bool> promise4;
-
-  future = collect(promise1.future(), promise4.future());
-
-  ASSERT_TRUE(future.isPending());
-
-  promise4.discard();
-
-  AWAIT_FAILED(future);
-}
-
-
-TEST(ProcessTest, Await1)
-{
-  ASSERT_TRUE(GTEST_IS_THREADSAFE);
-
-  // First ensure an empty list functions correctly.
-  std::list<Future<int>> empty;
-  Future<std::list<Future<int>>> future = await(empty);
-  AWAIT_ASSERT_READY(future);
-  EXPECT_TRUE(future.get().empty());
-
-  Promise<int> promise1;
-  Promise<int> promise2;
-  Promise<int> promise3;
-  Promise<int> promise4;
-
-  std::list<Future<int>> futures;
-  futures.push_back(promise1.future());
-  futures.push_back(promise2.future());
-  futures.push_back(promise3.future());
-  futures.push_back(promise4.future());
-
-  // Set them out-of-order.
-  promise4.set(4);
-  promise2.set(2);
-  promise1.set(1);
-  promise3.set(3);
-
-  future = await(futures);
-
-  AWAIT_ASSERT_READY(future);
-
-  EXPECT_EQ(futures.size(), future.get().size());
-
-  // We expect them to be returned in the same order as the
-  // future list that was passed in.
-  int i = 1;
-  foreach (const Future<int>& result, future.get()) {
-    ASSERT_TRUE(result.isReady());
-    ASSERT_EQ(i, result.get());
-    ++i;
-  }
-}
-
-
-TEST(ProcessTest, Await2)
-{
-  Promise<int> promise1;
-  Promise<bool> promise2;
-
-  Future<std::tuple<Future<int>, Future<bool>>> future =
-    await(promise1.future(), promise2.future());
-  ASSERT_TRUE(future.isPending());
-
-  promise1.set(42);
-
-  ASSERT_TRUE(future.isPending());
-
-  promise2.fail("failure message");
-
-  AWAIT_READY(future);
-
-  std::tuple<Future<int>, Future<bool>> futures = future.get();
-
-  ASSERT_TRUE(std::get<0>(futures).isReady());
-  ASSERT_EQ(42, std::get<0>(futures).get());
-
-  ASSERT_TRUE(std::get<1>(futures).isFailed());
-}
-
-
-TEST(ProcessTest, Await3)
-{
-  Promise<int> promise1;
-  Promise<bool> promise2;
-
-  Future<std::tuple<Future<int>, Future<bool>>> future =
-    await(promise1.future(), promise2.future());
-  ASSERT_TRUE(future.isPending());
-
-  promise1.set(42);
-
-  ASSERT_TRUE(future.isPending());
-
-  promise2.discard();
-
-  AWAIT_READY(future);
-
-  std::tuple<Future<int>, Future<bool>> futures = future.get();
-
-  ASSERT_TRUE(std::get<0>(futures).isReady());
-  ASSERT_EQ(42, std::get<0>(futures).get());
-
-  ASSERT_TRUE(std::get<1>(futures).isDiscarded());
-}
-
-
 class SettleProcess : public Process<SettleProcess>
 {
 public:


[4/7] mesos git commit: Minor cleanup in perf_tests.cpp.

Posted by bm...@apache.org.
Minor cleanup in perf_tests.cpp.

Review: https://reviews.apache.org/r/38378


Project: http://git-wip-us.apache.org/repos/asf/mesos/repo
Commit: http://git-wip-us.apache.org/repos/asf/mesos/commit/c647342c
Tree: http://git-wip-us.apache.org/repos/asf/mesos/tree/c647342c
Diff: http://git-wip-us.apache.org/repos/asf/mesos/diff/c647342c

Branch: refs/heads/master
Commit: c647342c502e6e29ac0f306d0e0705c31fdecbcc
Parents: 3949de2
Author: Benjamin Mahler <be...@gmail.com>
Authored: Mon Sep 14 13:13:46 2015 -0700
Committer: Benjamin Mahler <be...@gmail.com>
Committed: Mon Sep 14 16:56:20 2015 -0700

----------------------------------------------------------------------
 src/tests/containerizer/perf_tests.cpp | 11 +++--------
 1 file changed, 3 insertions(+), 8 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/mesos/blob/c647342c/src/tests/containerizer/perf_tests.cpp
----------------------------------------------------------------------
diff --git a/src/tests/containerizer/perf_tests.cpp b/src/tests/containerizer/perf_tests.cpp
index bef475e..9fceaa6 100644
--- a/src/tests/containerizer/perf_tests.cpp
+++ b/src/tests/containerizer/perf_tests.cpp
@@ -44,16 +44,11 @@ class PerfTest : public ::testing::Test {};
 
 TEST_F(PerfTest, ROOT_Events)
 {
-  set<string> events;
-
   // Valid events.
-  events.insert("cycles");
-  events.insert("task-clock");
-  EXPECT_TRUE(perf::valid(events));
+  EXPECT_TRUE(perf::valid({"cycles", "task-clock"}));
 
-  // Add an invalid event.
-  events.insert("this-is-an-invalid-event");
-  EXPECT_FALSE(perf::valid(events));
+  // Invalid event among valid events.
+  EXPECT_FALSE(perf::valid({"cycles", "task-clock", "invalid-event"}));
 }
 
 


[5/7] mesos git commit: Minor cleanups in the perf event isolator.

Posted by bm...@apache.org.
Minor cleanups in the perf event isolator.

Review: https://reviews.apache.org/r/38380


Project: http://git-wip-us.apache.org/repos/asf/mesos/repo
Commit: http://git-wip-us.apache.org/repos/asf/mesos/commit/a7a745d4
Tree: http://git-wip-us.apache.org/repos/asf/mesos/tree/a7a745d4
Diff: http://git-wip-us.apache.org/repos/asf/mesos/diff/a7a745d4

Branch: refs/heads/master
Commit: a7a745d4cd39bca0bcfa1c0bba784925ac411b13
Parents: a901529
Author: Benjamin Mahler <be...@gmail.com>
Authored: Mon Sep 14 14:23:08 2015 -0700
Committer: Benjamin Mahler <be...@gmail.com>
Committed: Mon Sep 14 17:04:44 2015 -0700

----------------------------------------------------------------------
 .../isolators/cgroups/perf_event.cpp            | 68 +++++++++-----------
 1 file changed, 30 insertions(+), 38 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/mesos/blob/a7a745d4/src/slave/containerizer/isolators/cgroups/perf_event.cpp
----------------------------------------------------------------------
diff --git a/src/slave/containerizer/isolators/cgroups/perf_event.cpp b/src/slave/containerizer/isolators/cgroups/perf_event.cpp
index a362182..dc8d3b1 100644
--- a/src/slave/containerizer/isolators/cgroups/perf_event.cpp
+++ b/src/slave/containerizer/isolators/cgroups/perf_event.cpp
@@ -369,44 +369,36 @@ Future<hashmap<string, PerfStatistics>> discardSample(
 
 void CgroupsPerfEventIsolatorProcess::sample()
 {
+  // Collect a perf sample for all cgroups that are not being
+  // destroyed. Since destroyal is asynchronous, 'perf stat' may
+  // fail if the cgroup is destroyed before running perf.
   set<string> cgroups;
+
   foreachvalue (Info* info, infos) {
     CHECK_NOTNULL(info);
 
-    if (info->destroying) {
-      // Skip cgroups if destroy has started because it's asynchronous
-      // and "perf stat" will fail if the cgroup has been destroyed
-      // by the time we actually run perf.
-      continue;
+    if (!info->destroying) {
+      cgroups.insert(info->cgroup);
     }
-
-    cgroups.insert(info->cgroup);
   }
 
-  if (cgroups.size() > 0) {
-    // The timeout includes an allowance of twice the process::reap
-    // interval (currently one second) to ensure we see the perf
-    // process exit. If the sample is not ready after the timeout
-    // something very unexpected has occurred so we discard it and
-    // halt all sampling.
-    Duration timeout = flags.perf_duration + Seconds(2);
-
-    perf::sample(events, cgroups, flags.perf_duration)
-      .after(timeout,
-             lambda::bind(&discardSample,
-                          lambda::_1,
-                          flags.perf_duration,
-                          timeout))
-      .onAny(defer(PID<CgroupsPerfEventIsolatorProcess>(this),
-                   &CgroupsPerfEventIsolatorProcess::_sample,
-                   Clock::now() + flags.perf_interval,
-                   lambda::_1));
-  } else {
-    // No cgroups to sample for now so just schedule the next sample.
-    delay(flags.perf_interval,
-          PID<CgroupsPerfEventIsolatorProcess>(this),
-          &CgroupsPerfEventIsolatorProcess::sample);
-  }
+  // The timeout includes an allowance of twice the process::reap
+  // interval (currently one second) to ensure we see the perf
+  // process exit. If the sample is not ready after the timeout
+  // something very unexpected has occurred so we discard it and
+  // halt all sampling.
+  Duration timeout = flags.perf_duration + Seconds(2);
+
+  perf::sample(events, cgroups, flags.perf_duration)
+    .after(timeout,
+           lambda::bind(&discardSample,
+                        lambda::_1,
+                        flags.perf_duration,
+                        timeout))
+    .onAny(defer(PID<CgroupsPerfEventIsolatorProcess>(this),
+                 &CgroupsPerfEventIsolatorProcess::_sample,
+                 Clock::now() + flags.perf_interval,
+                 lambda::_1));
 }
 
 
@@ -418,20 +410,20 @@ void CgroupsPerfEventIsolatorProcess::_sample(
     // Failure can occur for many reasons but all are unexpected and
     // indicate something is not right so we'll stop sampling.
     LOG(ERROR) << "Failed to get perf sample, sampling will be halted: "
-               << (statistics.isFailed() ? statistics.failure() : "discarded");
+               << (statistics.isFailed()
+                   ? statistics.failure()
+                   : "discarded due to timeout");
     return;
   }
 
+  // Store the latest statistics, note that cgroups added in the
+  // interim will be picked up by the next sample.
   foreachvalue (Info* info, infos) {
     CHECK_NOTNULL(info);
 
-    if (!statistics.get().contains(info->cgroup)) {
-      // This must be a newly added cgroup and isn't in this sample;
-      // it should be included in the next sample.
-      continue;
+    if (statistics->contains(info->cgroup)) {
+      info->statistics = statistics->get(info->cgroup).get();
     }
-
-    info->statistics = statistics.get().get(info->cgroup).get();
   }
 
   // Schedule sample for the next time.


[3/7] mesos git commit: Handle empty set of cgroups as a no-op in perf::sample.

Posted by bm...@apache.org.
Handle empty set of cgroups as a no-op in perf::sample.

Review: https://reviews.apache.org/r/38379


Project: http://git-wip-us.apache.org/repos/asf/mesos/repo
Commit: http://git-wip-us.apache.org/repos/asf/mesos/commit/a901529f
Tree: http://git-wip-us.apache.org/repos/asf/mesos/tree/a901529f
Diff: http://git-wip-us.apache.org/repos/asf/mesos/diff/a901529f

Branch: refs/heads/master
Commit: a901529fe2278caf87a7ada6832f49257db19266
Parents: c647342
Author: Benjamin Mahler <be...@gmail.com>
Authored: Mon Sep 14 13:15:58 2015 -0700
Committer: Benjamin Mahler <be...@gmail.com>
Committed: Mon Sep 14 16:56:20 2015 -0700

----------------------------------------------------------------------
 src/linux/perf.cpp                     |  5 +++++
 src/tests/containerizer/perf_tests.cpp | 12 ++++++++++++
 2 files changed, 17 insertions(+)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/mesos/blob/a901529f/src/linux/perf.cpp
----------------------------------------------------------------------
diff --git a/src/linux/perf.cpp b/src/linux/perf.cpp
index 0011482..f7035dd 100644
--- a/src/linux/perf.cpp
+++ b/src/linux/perf.cpp
@@ -310,6 +310,11 @@ Future<hashmap<string, mesos::PerfStatistics>> sample(
     const set<string>& cgroups,
     const Duration& duration)
 {
+  // Is this a no-op?
+  if (cgroups.empty()) {
+    return hashmap<string, mesos::PerfStatistics>();
+  }
+
   vector<string> argv = {
     "stat",
 

http://git-wip-us.apache.org/repos/asf/mesos/blob/a901529f/src/tests/containerizer/perf_tests.cpp
----------------------------------------------------------------------
diff --git a/src/tests/containerizer/perf_tests.cpp b/src/tests/containerizer/perf_tests.cpp
index 9fceaa6..ed5212e 100644
--- a/src/tests/containerizer/perf_tests.cpp
+++ b/src/tests/containerizer/perf_tests.cpp
@@ -52,6 +52,18 @@ TEST_F(PerfTest, ROOT_Events)
 }
 
 
+TEST_F(PerfTest, ROOT_Sample)
+{
+  // Sampling an empty set of cgroups should be a no-op.
+  Future<hashmap<string, PerfStatistics>> sample =
+    perf::sample({"cycles", "task-clock"}, {}, Seconds(1));
+
+  AWAIT_READY(sample);
+
+  EXPECT_TRUE(sample->empty());
+}
+
+
 TEST_F(PerfTest, Parse)
 {
   // Parse multiple cgroups with uint64 and floats.


[6/7] mesos git commit: Removed hard-coded reap interval from perf event isolator.

Posted by bm...@apache.org.
Removed hard-coded reap interval from perf event isolator.

Review: https://reviews.apache.org/r/38381


Project: http://git-wip-us.apache.org/repos/asf/mesos/repo
Commit: http://git-wip-us.apache.org/repos/asf/mesos/commit/72f84529
Tree: http://git-wip-us.apache.org/repos/asf/mesos/tree/72f84529
Diff: http://git-wip-us.apache.org/repos/asf/mesos/diff/72f84529

Branch: refs/heads/master
Commit: 72f8452918a50f73071f168ec85bfd80ac43a639
Parents: a7a745d
Author: Benjamin Mahler <be...@gmail.com>
Authored: Mon Sep 14 14:41:21 2015 -0700
Committer: Benjamin Mahler <be...@gmail.com>
Committed: Mon Sep 14 17:04:45 2015 -0700

----------------------------------------------------------------------
 src/slave/containerizer/isolators/cgroups/perf_event.cpp | 10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/mesos/blob/72f84529/src/slave/containerizer/isolators/cgroups/perf_event.cpp
----------------------------------------------------------------------
diff --git a/src/slave/containerizer/isolators/cgroups/perf_event.cpp b/src/slave/containerizer/isolators/cgroups/perf_event.cpp
index dc8d3b1..f6ab8bc 100644
--- a/src/slave/containerizer/isolators/cgroups/perf_event.cpp
+++ b/src/slave/containerizer/isolators/cgroups/perf_event.cpp
@@ -28,6 +28,7 @@
 #include <process/delay.hpp>
 #include <process/io.hpp>
 #include <process/pid.hpp>
+#include <process/reap.hpp>
 #include <process/subprocess.hpp>
 
 #include <stout/bytes.hpp>
@@ -383,11 +384,10 @@ void CgroupsPerfEventIsolatorProcess::sample()
   }
 
   // The timeout includes an allowance of twice the process::reap
-  // interval (currently one second) to ensure we see the perf
-  // process exit. If the sample is not ready after the timeout
-  // something very unexpected has occurred so we discard it and
-  // halt all sampling.
-  Duration timeout = flags.perf_duration + Seconds(2);
+  // interval to ensure we see the perf process exit. If the sample
+  // is not ready after the timeout something very unexpected has
+  // occurred so we discard it and halt all sampling.
+  Duration timeout = flags.perf_duration + process::MAX_REAP_INTERVAL() * 2;
 
   perf::sample(events, cgroups, flags.perf_duration)
     .after(timeout,