You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@mesos.apache.org by ji...@apache.org on 2017/08/04 23:01:00 UTC

[1/3] mesos git commit: Made the rlimits isolator work with nested containers.

Repository: mesos
Updated Branches:
  refs/heads/master 13953dc4b -> 50a553dd1


Made the rlimits isolator work with nested containers.

Make the rlimits isolator support nesting. Without this patch rlimits
sets for tasks launched by the DefaultExecutor are silently ignored.

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


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

Branch: refs/heads/master
Commit: 21a3405aaa189328a774f031d55c71df56fd0b4f
Parents: 13953dc
Author: Gastón Kleiman <ga...@mesosphere.io>
Authored: Fri Aug 4 15:29:47 2017 -0700
Committer: Jie Yu <yu...@gmail.com>
Committed: Fri Aug 4 15:44:02 2017 -0700

----------------------------------------------------------------------
 .../mesos/isolators/posix/rlimits.cpp           |   6 +
 .../mesos/isolators/posix/rlimits.hpp           |   2 +
 .../posix_rlimits_isolator_tests.cpp            | 178 +++++++++++++++++++
 3 files changed, 186 insertions(+)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/mesos/blob/21a3405a/src/slave/containerizer/mesos/isolators/posix/rlimits.cpp
----------------------------------------------------------------------
diff --git a/src/slave/containerizer/mesos/isolators/posix/rlimits.cpp b/src/slave/containerizer/mesos/isolators/posix/rlimits.cpp
index 3fc2b3d..0136652 100644
--- a/src/slave/containerizer/mesos/isolators/posix/rlimits.cpp
+++ b/src/slave/containerizer/mesos/isolators/posix/rlimits.cpp
@@ -28,6 +28,12 @@ namespace mesos {
 namespace internal {
 namespace slave {
 
+bool PosixRLimitsIsolatorProcess::supportsNesting()
+{
+  return true;
+}
+
+
 process::Future<Option<ContainerLaunchInfo>>
 PosixRLimitsIsolatorProcess::prepare(
     const ContainerID& containerId,

http://git-wip-us.apache.org/repos/asf/mesos/blob/21a3405a/src/slave/containerizer/mesos/isolators/posix/rlimits.hpp
----------------------------------------------------------------------
diff --git a/src/slave/containerizer/mesos/isolators/posix/rlimits.hpp b/src/slave/containerizer/mesos/isolators/posix/rlimits.hpp
index ee36a24..0bce083 100644
--- a/src/slave/containerizer/mesos/isolators/posix/rlimits.hpp
+++ b/src/slave/containerizer/mesos/isolators/posix/rlimits.hpp
@@ -32,6 +32,8 @@ class PosixRLimitsIsolatorProcess : public MesosIsolatorProcess
 public:
   static Try<mesos::slave::Isolator*> create(const Flags& flags);
 
+  virtual bool supportsNesting();
+
   virtual process::Future<Option<mesos::slave::ContainerLaunchInfo>> prepare(
       const ContainerID& containerId,
       const mesos::slave::ContainerConfig& containerConfig);

http://git-wip-us.apache.org/repos/asf/mesos/blob/21a3405a/src/tests/containerizer/posix_rlimits_isolator_tests.cpp
----------------------------------------------------------------------
diff --git a/src/tests/containerizer/posix_rlimits_isolator_tests.cpp b/src/tests/containerizer/posix_rlimits_isolator_tests.cpp
index b7ccc7e..3d87a78 100644
--- a/src/tests/containerizer/posix_rlimits_isolator_tests.cpp
+++ b/src/tests/containerizer/posix_rlimits_isolator_tests.cpp
@@ -31,6 +31,8 @@
 #include <mesos/mesos.hpp>
 #include <mesos/scheduler.hpp>
 
+#include <stout/hashmap.hpp>
+
 #include "slave/flags.hpp"
 #include "tests/cluster.hpp"
 #include "tests/environment.hpp"
@@ -338,6 +340,182 @@ TEST_F(PosixRLimitsIsolatorTest, TaskExceedingLimit)
   driver.join();
 }
 
+
+// This test confirms that rlimits are set for nested containers.
+TEST_F(PosixRLimitsIsolatorTest, NestedContainers)
+{
+  Try<Owned<cluster::Master>> master = StartMaster();
+  ASSERT_SOME(master);
+
+  slave::Flags flags = CreateSlaveFlags();
+  flags.isolation = "posix/rlimits";
+
+#ifndef USE_SSL_SOCKET
+  // Disable operator API authentication for the default executor.
+  // Executor authentication currently has SSL as a dependency, so we
+  // cannot require executors to authenticate with the agent operator
+  // API if Mesos was not built with SSL support.
+  flags.authenticate_http_readwrite = false;
+#endif // USE_SSL_SOCKET
+
+  Owned<MasterDetector> detector = master.get()->createDetector();
+
+  Try<Owned<cluster::Slave>> slave = StartSlave(detector.get(), flags);
+  ASSERT_SOME(slave);
+
+  MockScheduler sched;
+
+  MesosSchedulerDriver driver(
+      &sched,
+      DEFAULT_FRAMEWORK_INFO,
+      master.get()->pid,
+      DEFAULT_CREDENTIAL);
+
+  Future<FrameworkID> frameworkId;
+  EXPECT_CALL(sched, registered(&driver, _, _))
+    .WillOnce(FutureArg<1>(&frameworkId));
+
+  Future<vector<Offer>> offers;
+  EXPECT_CALL(sched, resourceOffers(_, _))
+      .WillOnce(FutureArg<1>(&offers))
+      .WillRepeatedly(Return()); // Ignore subsequent offers.
+
+  driver.start();
+
+  AWAIT_READY(frameworkId);
+
+  AWAIT_READY(offers);
+  ASSERT_NE(0u, offers->size());
+
+  Future<TaskStatus> taskStatuses[4];
+
+  {
+    // This variable doesn't have to be used explicitly.
+    testing::InSequence inSequence;
+
+    foreach (Future<TaskStatus>& taskStatus, taskStatuses) {
+      EXPECT_CALL(sched, statusUpdate(&driver, _))
+          .WillOnce(FutureArg<1>(&taskStatus));
+    }
+
+    EXPECT_CALL(sched, statusUpdate(&driver, _))
+        .WillRepeatedly(Return()); // Ignore subsequent updates.
+  }
+
+  Resources resources = Resources::parse("cpus:0.1;mem:32;disk:32").get();
+
+  const Offer& offer = offers->front();
+  const SlaveID& slaveId = offer.slave_id();
+
+  TaskInfo task1 = createTask(
+      slaveId,
+      resources,
+      "ULIMIT=`ulimit -t`;\n"
+      "if [ \"$ULIMIT\" != \"10000\" ]; then\n"
+      "  exit 1;\n"
+      "fi");
+
+  {
+    TaskID taskId;
+    taskId.set_value("task1");
+
+    task1.mutable_task_id()->CopyFrom(taskId);
+
+    ContainerInfo* container = task1.mutable_container();
+    container->set_type(ContainerInfo::MESOS);
+
+    RLimitInfo rlimitInfo;
+    RLimitInfo::RLimit* cpuLimit = rlimitInfo.add_rlimits();
+    cpuLimit->set_type(RLimitInfo::RLimit::RLMT_CPU);
+    cpuLimit->set_soft(10000);
+    cpuLimit->set_hard(10000);
+
+    container->mutable_rlimit_info()->CopyFrom(rlimitInfo);
+  }
+
+  TaskInfo task2 = createTask(
+      slaveId,
+      resources,
+      "ULIMIT=`ulimit -t`;\n"
+      "if [ \"$ULIMIT\" != \"20000\" ]; then\n"
+      "  exit 1;\n"
+      "fi");
+
+  {
+    TaskID taskId;
+    taskId.set_value("task2");
+
+    task2.mutable_task_id()->CopyFrom(taskId);
+
+    ContainerInfo* container = task2.mutable_container();
+    container->set_type(ContainerInfo::MESOS);
+
+    RLimitInfo rlimitInfo;
+    RLimitInfo::RLimit* cpuLimit = rlimitInfo.add_rlimits();
+    cpuLimit->set_type(RLimitInfo::RLimit::RLMT_CPU);
+    cpuLimit->set_soft(20000);
+    cpuLimit->set_hard(20000);
+
+    container->mutable_rlimit_info()->CopyFrom(rlimitInfo);
+  }
+
+  TaskGroupInfo taskGroup = createTaskGroupInfo({task1, task2});
+
+  ExecutorInfo executorInfo;
+  executorInfo.set_type(ExecutorInfo::DEFAULT);
+  executorInfo.mutable_executor_id()->CopyFrom(DEFAULT_EXECUTOR_ID);
+  executorInfo.mutable_framework_id()->CopyFrom(frameworkId.get());
+  executorInfo.mutable_resources()->CopyFrom(resources);
+
+  driver.acceptOffers(
+      {offer.id()},
+      {LAUNCH_GROUP(executorInfo, taskGroup)});
+
+  // We track the status updates of each task separately, to verify
+  // that they transition from TASK_RUNNING to TASK_FINISHED.
+  enum class Stage
+  {
+    INITIAL,
+    RUNNING,
+    FINISHED
+  };
+
+  hashmap<TaskID, Stage> taskStages;
+  taskStages[task1.task_id()] = Stage::INITIAL;
+  taskStages[task2.task_id()] = Stage::INITIAL;
+
+  foreach (const Future<TaskStatus>& taskStatus, taskStatuses) {
+    AWAIT_READY(taskStatus);
+
+    Option<Stage> taskStage = taskStages.get(taskStatus->task_id());
+    ASSERT_SOME(taskStage);
+
+    switch (taskStage.get()) {
+      case Stage::INITIAL: {
+        ASSERT_EQ(TASK_RUNNING, taskStatus->state())
+          << taskStatus->DebugString();
+
+        taskStages[taskStatus->task_id()] = Stage::RUNNING;
+        break;
+      }
+      case Stage::RUNNING: {
+        ASSERT_EQ(TASK_FINISHED, taskStatus->state())
+          << taskStatus->DebugString();
+
+        taskStages[taskStatus->task_id()] = Stage::FINISHED;
+        break;
+      }
+      case Stage::FINISHED: {
+        FAIL() << "Unexpected task update: " << taskStatus->DebugString();
+        break;
+      }
+    }
+  }
+
+  driver.stop();
+  driver.join();
+}
+
 } // namespace tests {
 } // namespace internal {
 } // namespace mesos {


[3/3] mesos git commit: Made the capabilities isolator work with nested containers.

Posted by ji...@apache.org.
Made the capabilities isolator work with nested containers.

Make the capabilities isolator support nesting. Without this patch
capabilities sets for tasks launched by the DefaultExecutor are silently
ignored.

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


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

Branch: refs/heads/master
Commit: 50a553dd10a2adbf653d5ad751723294a14720a8
Parents: cbb2262
Author: Gastón Kleiman <ga...@mesosphere.io>
Authored: Fri Aug 4 15:51:27 2017 -0700
Committer: Jie Yu <yu...@gmail.com>
Committed: Fri Aug 4 15:51:27 2017 -0700

----------------------------------------------------------------------
 .../mesos/isolators/linux/capabilities.cpp      |   6 +
 .../mesos/isolators/linux/capabilities.hpp      |   2 +
 .../linux_capabilities_isolator_tests.cpp       | 147 +++++++++++++++++++
 3 files changed, 155 insertions(+)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/mesos/blob/50a553dd/src/slave/containerizer/mesos/isolators/linux/capabilities.cpp
----------------------------------------------------------------------
diff --git a/src/slave/containerizer/mesos/isolators/linux/capabilities.cpp b/src/slave/containerizer/mesos/isolators/linux/capabilities.cpp
index f85a84d..21d851e 100644
--- a/src/slave/containerizer/mesos/isolators/linux/capabilities.cpp
+++ b/src/slave/containerizer/mesos/isolators/linux/capabilities.cpp
@@ -74,6 +74,12 @@ Try<Isolator*> LinuxCapabilitiesIsolatorProcess::create(const Flags& flags)
 }
 
 
+bool LinuxCapabilitiesIsolatorProcess::supportsNesting()
+{
+  return true;
+}
+
+
 Future<Option<ContainerLaunchInfo>> LinuxCapabilitiesIsolatorProcess::prepare(
     const ContainerID& containerId,
     const ContainerConfig& containerConfig)

http://git-wip-us.apache.org/repos/asf/mesos/blob/50a553dd/src/slave/containerizer/mesos/isolators/linux/capabilities.hpp
----------------------------------------------------------------------
diff --git a/src/slave/containerizer/mesos/isolators/linux/capabilities.hpp b/src/slave/containerizer/mesos/isolators/linux/capabilities.hpp
index c3afe20..b9862a2 100644
--- a/src/slave/containerizer/mesos/isolators/linux/capabilities.hpp
+++ b/src/slave/containerizer/mesos/isolators/linux/capabilities.hpp
@@ -32,6 +32,8 @@ class LinuxCapabilitiesIsolatorProcess : public MesosIsolatorProcess
 public:
   static Try<mesos::slave::Isolator*> create(const Flags& flags);
 
+  virtual bool supportsNesting();
+
   virtual process::Future<Option<mesos::slave::ContainerLaunchInfo>> prepare(
       const ContainerID& containerId,
       const mesos::slave::ContainerConfig& containerConfig);

http://git-wip-us.apache.org/repos/asf/mesos/blob/50a553dd/src/tests/containerizer/linux_capabilities_isolator_tests.cpp
----------------------------------------------------------------------
diff --git a/src/tests/containerizer/linux_capabilities_isolator_tests.cpp b/src/tests/containerizer/linux_capabilities_isolator_tests.cpp
index 8050876..6d95d60 100644
--- a/src/tests/containerizer/linux_capabilities_isolator_tests.cpp
+++ b/src/tests/containerizer/linux_capabilities_isolator_tests.cpp
@@ -41,6 +41,8 @@
 
 #include <mesos/master/detector.hpp>
 
+#include <mesos/resources.hpp>
+
 #include "linux/capabilities.hpp"
 
 #include "master/detector/standalone.hpp"
@@ -328,6 +330,151 @@ TEST_P(LinuxCapabilitiesIsolatorTest, ROOT_Ping)
 }
 
 
+// Parameterized test confirming the behavior of the capabilities
+// isolator with nested containers. We here use the fact has `ping`
+// has `NET_RAW` and `NET_ADMIN` in its file capabilities. This test
+// should be instantiated with above `TestParam` struct.
+TEST_P(LinuxCapabilitiesIsolatorTest, ROOT_NestedPing)
+{
+  Try<Owned<cluster::Master>> master = StartMaster();
+  ASSERT_SOME(master);
+
+  slave::Flags flags = CreateSlaveFlags();
+  flags.isolation = "linux/capabilities";
+  flags.effective_capabilities = param.operator_effective;
+  flags.bounding_capabilities = param.operator_bounding;
+
+#ifndef USE_SSL_SOCKET
+  // Disable operator API authentication for the default executor. Executor
+  // authentication currently has SSL as a dependency, so we cannot require
+  // executors to authenticate with the agent operator API if Mesos was not
+  // built with SSL support.
+  flags.authenticate_http_readwrite = false;
+#endif // USE_SSL_SOCKET
+
+  if (param.useImage == TestParam::WITH_IMAGE) {
+    const string registry = path::join(sandbox.get(), "registry");
+    AWAIT_READY(DockerArchive::create(registry, "test_image"));
+
+    flags.docker_registry = registry;
+    flags.docker_store_dir = path::join(os::getcwd(), "store");
+    flags.image_providers = "docker";
+    flags.isolation += ",docker/runtime,filesystem/linux";
+  }
+
+  Owned<MasterDetector> detector = master.get()->createDetector();
+
+  Try<Owned<cluster::Slave>> slave = StartSlave(detector.get(), flags);
+  ASSERT_SOME(slave);
+
+  MockScheduler sched;
+
+  MesosSchedulerDriver driver(
+      &sched,
+      DEFAULT_FRAMEWORK_INFO,
+      master.get()->pid,
+      DEFAULT_CREDENTIAL);
+
+  Future<FrameworkID> frameworkId;
+  EXPECT_CALL(sched, registered(&driver, _, _))
+    .WillOnce(FutureArg<1>(&frameworkId));
+
+  Future<vector<Offer>> offers;
+
+  EXPECT_CALL(sched, resourceOffers(_, _))
+    .WillOnce(FutureArg<1>(&offers))
+    .WillRepeatedly(Return()); // Ignore subsequent offers.
+
+  driver.start();
+
+  AWAIT_READY(frameworkId);
+
+  AWAIT_READY(offers);
+  ASSERT_NE(0u, offers->size());
+
+  Resources resources = Resources::parse("cpus:0.1;mem:32;disk:32").get();
+
+  ExecutorInfo executorInfo;
+  executorInfo.set_type(ExecutorInfo::DEFAULT);
+  executorInfo.mutable_executor_id()->CopyFrom(DEFAULT_EXECUTOR_ID);
+  executorInfo.mutable_framework_id()->CopyFrom(frameworkId.get());
+  executorInfo.mutable_resources()->CopyFrom(resources);
+
+  const Offer& offer = offers->front();
+  const SlaveID& slaveId = offer.slave_id();
+
+  // We use 'ping' as the command since it has file capabilities
+  // (`NET_RAW` and `NET_ADMIN` in permitted set). This allows us to
+  // test if capabilities are properly set.
+  CommandInfo command;
+  command.set_shell(false);
+  command.set_value("/bin/ping");
+  command.add_arguments("ping");
+  command.add_arguments("-c");
+  command.add_arguments("1");
+  command.add_arguments("127.0.0.1");
+
+  TaskInfo task = createTask(slaveId, resources, command);
+
+  if (param.framework_effective.isSome() ||
+      param.framework_bounding.isSome()) {
+    ContainerInfo* container = task.mutable_container();
+    container->set_type(ContainerInfo::MESOS);
+
+    LinuxInfo* linux = container->mutable_linux_info();
+
+    if (param.framework_effective.isSome()) {
+      CapabilityInfo* capabilities = linux->mutable_effective_capabilities();
+      capabilities->CopyFrom(param.framework_effective.get());
+    }
+
+    if (param.framework_bounding.isSome()) {
+      CapabilityInfo* capabilities = linux->mutable_bounding_capabilities();
+      capabilities->CopyFrom(param.framework_bounding.get());
+    }
+  }
+
+  if (param.useImage == TestParam::WITH_IMAGE) {
+    ContainerInfo* container = task.mutable_container();
+    container->set_type(ContainerInfo::MESOS);
+
+    Image* image = container->mutable_mesos()->mutable_image();
+    image->set_type(Image::DOCKER);
+    image->mutable_docker()->set_name("test_image");
+  }
+
+  Queue<TaskStatus> statuses;
+  EXPECT_CALL(sched, statusUpdate(_, _))
+    .WillRepeatedly(PushTaskStatus<1>(&statuses));
+
+  TaskGroupInfo taskGroup = createTaskGroupInfo({task});
+
+  driver.acceptOffers({offer.id()}, {LAUNCH_GROUP(executorInfo, taskGroup)});
+
+  // Wait for the terminal status update.
+  for (;;) {
+    Future<TaskStatus> status = statuses.get();
+    AWAIT_READY(status);
+
+    TaskState state = status->state();
+    if (protobuf::isTerminalState(state)) {
+      switch (param.result) {
+        case TestParam::SUCCESS:
+          EXPECT_EQ(TASK_FINISHED, state) << status->DebugString();
+          break;
+        case TestParam::FAILURE:
+          EXPECT_EQ(TASK_FAILED, state) << status->DebugString();
+          break;
+      }
+      break;
+    }
+  }
+
+  driver.stop();
+  driver.join();
+}
+
+
 // TODO(jieyu): We used DAC_READ_SEARCH capability below so that test
 // results won't be affected even if the executable (e.g., command
 // executor) to launch is not accessible (e.g., under someone's home


[2/3] mesos git commit: Fixed some style issues in posix rlimits isolator tests.

Posted by ji...@apache.org.
Fixed some style issues in posix rlimits isolator tests.


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

Branch: refs/heads/master
Commit: cbb2262dbe45f9303281518e58baf907db6ee4af
Parents: 21a3405
Author: Jie Yu <yu...@gmail.com>
Authored: Fri Aug 4 15:46:29 2017 -0700
Committer: Jie Yu <yu...@gmail.com>
Committed: Fri Aug 4 15:46:29 2017 -0700

----------------------------------------------------------------------
 .../posix_rlimits_isolator_tests.cpp            | 35 ++++++++++----------
 1 file changed, 18 insertions(+), 17 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/mesos/blob/cbb2262d/src/tests/containerizer/posix_rlimits_isolator_tests.cpp
----------------------------------------------------------------------
diff --git a/src/tests/containerizer/posix_rlimits_isolator_tests.cpp b/src/tests/containerizer/posix_rlimits_isolator_tests.cpp
index 3d87a78..bf25049 100644
--- a/src/tests/containerizer/posix_rlimits_isolator_tests.cpp
+++ b/src/tests/containerizer/posix_rlimits_isolator_tests.cpp
@@ -79,8 +79,8 @@ TEST_F(PosixRLimitsIsolatorTest, InvalidLimits)
   Future<vector<Offer>> offers;
 
   EXPECT_CALL(sched, resourceOffers(_, _))
-      .WillOnce(FutureArg<1>(&offers))
-      .WillRepeatedly(Return()); // Ignore subsequent offers.
+    .WillOnce(FutureArg<1>(&offers))
+    .WillRepeatedly(Return()); // Ignore subsequent offers.
 
   driver.start();
 
@@ -106,7 +106,7 @@ TEST_F(PosixRLimitsIsolatorTest, InvalidLimits)
 
   Future<TaskStatus> taskStatus;
   EXPECT_CALL(sched, statusUpdate(&driver, _))
-      .WillOnce(FutureArg<1>(&taskStatus));
+    .WillOnce(FutureArg<1>(&taskStatus));
 
   driver.launchTasks(offers.get()[0].id(), {task});
 
@@ -122,7 +122,8 @@ TEST_F(PosixRLimitsIsolatorTest, InvalidLimits)
 
 // This test confirms that setting no values for the soft and hard
 // limits implies an unlimited resource.
-TEST_F(PosixRLimitsIsolatorTest, UnsetLimits) {
+TEST_F(PosixRLimitsIsolatorTest, UnsetLimits)
+{
   Try<Owned<cluster::Master>> master = StartMaster();
   ASSERT_SOME(master);
 
@@ -147,8 +148,8 @@ TEST_F(PosixRLimitsIsolatorTest, UnsetLimits) {
   Future<vector<Offer>> offers;
 
   EXPECT_CALL(sched, resourceOffers(_, _))
-      .WillOnce(FutureArg<1>(&offers))
-      .WillRepeatedly(Return()); // Ignore subsequent offers.
+    .WillOnce(FutureArg<1>(&offers))
+    .WillRepeatedly(Return()); // Ignore subsequent offers.
 
   driver.start();
 
@@ -181,8 +182,8 @@ TEST_F(PosixRLimitsIsolatorTest, UnsetLimits) {
   Future<TaskStatus> statusRunning;
   Future<TaskStatus> statusFinal;
   EXPECT_CALL(sched, statusUpdate(&driver, _))
-      .WillOnce(FutureArg<1>(&statusRunning))
-      .WillOnce(FutureArg<1>(&statusFinal));
+    .WillOnce(FutureArg<1>(&statusRunning))
+    .WillOnce(FutureArg<1>(&statusFinal));
 
   driver.launchTasks(offers.get()[0].id(), {task});
 
@@ -227,8 +228,8 @@ TEST_F(PosixRLimitsIsolatorTest, BothSoftAndHardLimitSet)
   Future<vector<Offer>> offers;
 
   EXPECT_CALL(sched, resourceOffers(_, _))
-      .WillOnce(FutureArg<1>(&offers))
-      .WillRepeatedly(Return()); // Ignore subsequent offers.
+    .WillOnce(FutureArg<1>(&offers))
+    .WillRepeatedly(Return()); // Ignore subsequent offers.
 
   driver.start();
 
@@ -252,7 +253,7 @@ TEST_F(PosixRLimitsIsolatorTest, BothSoftAndHardLimitSet)
 
   Future<TaskStatus> status;
   EXPECT_CALL(sched, statusUpdate(&driver, _))
-      .WillOnce(FutureArg<1>(&status));
+    .WillOnce(FutureArg<1>(&status));
 
   driver.launchTasks(offers.get()[0].id(), {task});
 
@@ -294,8 +295,8 @@ TEST_F(PosixRLimitsIsolatorTest, TaskExceedingLimit)
   Future<vector<Offer>> offers;
 
   EXPECT_CALL(sched, resourceOffers(_, _))
-      .WillOnce(FutureArg<1>(&offers))
-      .WillRepeatedly(Return()); // Ignore subsequent offers.
+    .WillOnce(FutureArg<1>(&offers))
+    .WillRepeatedly(Return()); // Ignore subsequent offers.
 
   driver.start();
 
@@ -377,8 +378,8 @@ TEST_F(PosixRLimitsIsolatorTest, NestedContainers)
 
   Future<vector<Offer>> offers;
   EXPECT_CALL(sched, resourceOffers(_, _))
-      .WillOnce(FutureArg<1>(&offers))
-      .WillRepeatedly(Return()); // Ignore subsequent offers.
+    .WillOnce(FutureArg<1>(&offers))
+    .WillRepeatedly(Return()); // Ignore subsequent offers.
 
   driver.start();
 
@@ -395,11 +396,11 @@ TEST_F(PosixRLimitsIsolatorTest, NestedContainers)
 
     foreach (Future<TaskStatus>& taskStatus, taskStatuses) {
       EXPECT_CALL(sched, statusUpdate(&driver, _))
-          .WillOnce(FutureArg<1>(&taskStatus));
+        .WillOnce(FutureArg<1>(&taskStatus));
     }
 
     EXPECT_CALL(sched, statusUpdate(&driver, _))
-        .WillRepeatedly(Return()); // Ignore subsequent updates.
+      .WillRepeatedly(Return()); // Ignore subsequent updates.
   }
 
   Resources resources = Resources::parse("cpus:0.1;mem:32;disk:32").get();