Repository: mesos
Updated Branches:
  refs/heads/master 5acea829b -> df05b63f1


Add 'max_num_executors' flag for use with network isolation

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


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

Branch: refs/heads/master
Commit: df05b63f1ebb988fbb65acc02be93b64674a0475
Parents: 5acea82
Author: Dominic Hamon <[email protected]>
Authored: Tue Aug 5 11:09:56 2014 -0700
Committer: Dominic Hamon <[email protected]>
Committed: Tue Aug 5 15:11:54 2014 -0700

----------------------------------------------------------------------
 src/master/flags.hpp       | 10 ++++++++++
 src/master/master.cpp      | 22 +++++++++++++++++++++
 src/tests/master_tests.cpp | 42 +++++++++++++++++++++++++++++++++++++++++
 3 files changed, 74 insertions(+)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/mesos/blob/df05b63f/src/master/flags.hpp
----------------------------------------------------------------------
diff --git a/src/master/flags.hpp b/src/master/flags.hpp
index 2b92de3..0db4c95 100644
--- a/src/master/flags.hpp
+++ b/src/master/flags.hpp
@@ -284,6 +284,12 @@ public:
         "  ],\n"
         "  \"aggregate_default_qps\": 33.3\n"
         "}");
+
+#ifdef WITH_NETWORK_ISOLATOR
+    add(&Flags::max_executors_per_slave,
+        "max_executors_per_slave",
+        "A maximum number of executors to allow per slave.");
+#endif  // WITH_NETWORK_ISOLATOR
   }
 
   bool version;
@@ -312,6 +318,10 @@ public:
   Option<std::string> credentials;
   Option<ACLs> acls;
   Option<RateLimits> rate_limits;
+
+#ifdef WITH_NETWORK_ISOLATOR
+  Option<size_t> max_executors_per_slave;
+#endif  // WITH_NETWORK_ISOLATOR
 };
 
 } // namespace master {

http://git-wip-us.apache.org/repos/asf/mesos/blob/df05b63f/src/master/master.cpp
----------------------------------------------------------------------
diff --git a/src/master/master.cpp b/src/master/master.cpp
index 5630680..9bede96 100644
--- a/src/master/master.cpp
+++ b/src/master/master.cpp
@@ -3416,6 +3416,28 @@ void Master::offer(const FrameworkID& frameworkId,
       continue;
     }
 
+#ifdef WITH_NETWORK_ISOLATOR
+    // TODO(dhamon): This flag is required as the static allocation of
+    // ephemeral ports leads to a maximum number of containers that can
+    // be created on each slave. Once MESOS-1654 is fixed and ephemeral
+    // ports are a first class resource, this can be removed.
+    if (flags.max_executors_per_slave.isSome()) {
+      // Check that we haven't hit the executor limit.
+      size_t numExecutors = 0;
+      foreachkey (const FrameworkID& frameworkId, slave->executors) {
+        numExecutors += slave->executors[frameworkId].keys().size();
+      }
+
+      if (numExecutors >= flags.max_executors_per_slave.get()) {
+        LOG(WARNING) << "Master returning resources offered because slave "
+                     << *slave << " has reached the maximum number of "
+                     << "executors";
+        allocator->resourcesRecovered(frameworkId, slaveId, offered);
+        continue;
+      }
+    }
+#endif  // WITH_NETWORK_ISOLATOR
+
     Offer* offer = new Offer();
     offer->mutable_id()->MergeFrom(newOfferId());
     offer->mutable_framework_id()->MergeFrom(framework->id);

http://git-wip-us.apache.org/repos/asf/mesos/blob/df05b63f/src/tests/master_tests.cpp
----------------------------------------------------------------------
diff --git a/src/tests/master_tests.cpp b/src/tests/master_tests.cpp
index 87bd8c0..9a1a373 100644
--- a/src/tests/master_tests.cpp
+++ b/src/tests/master_tests.cpp
@@ -2004,3 +2004,45 @@ TEST_F(MasterTest, OrphanTasks)
 
   Shutdown();
 }
+
+
+#ifdef WITH_NETWORK_ISOLATOR
+TEST_F(MasterTest, MaxExecutorsPerSlave)
+{
+  master::Flags flags = CreateMasterFlags();
+  flags.max_executors_per_slave = 0;
+
+  Try<PID<Master> > master = StartMaster(flags);
+  ASSERT_SOME(master);
+
+  MockExecutor exec(DEFAULT_EXECUTOR_ID);
+
+  TestContainerizer containerizer(&exec);
+
+  Try<PID<Slave> > slave = StartSlave(&containerizer);
+  ASSERT_SOME(slave);
+
+  MockScheduler sched;
+  MesosSchedulerDriver driver(
+      &sched, DEFAULT_FRAMEWORK_INFO, master.get(), DEFAULT_CREDENTIAL);
+
+  Future<MasterInfo> masterInfo;
+  EXPECT_CALL(sched, registered(&driver, _, _))
+    .WillOnce(FutureArg<2>(&masterInfo));
+
+  Future<vector<Offer> > offers;
+  EXPECT_CALL(sched, resourceOffers(&driver, _))
+    .Times(0);
+
+  driver.start();
+
+  AWAIT_READY(masterInfo);
+  EXPECT_EQ(master.get().port, masterInfo.get().port());
+  EXPECT_EQ(master.get().ip, masterInfo.get().ip());
+
+  driver.stop();
+  driver.join();
+
+  Shutdown(); // Must shutdown before 'containerizer' gets deallocated.
+}
+#endif  // WITH_NETWORK_ISOLATOR

Reply via email to