From c0c76a68a17ee4a7137a8f516087c8389a3eba07 Mon Sep 17 00:00:00 2001 From: Jan Olszak Date: Wed, 2 Sep 2015 17:04:45 +0200 Subject: [PATCH] lxcpp: Command implementation [Feature] Base class for commands Attach command [Cause] N/A [Solution] N/A [Verification] Build, install, run tests Change-Id: Id9ed43c145704f5d9d21f1aa210694fed1615c57 --- .../commands/{attach-manager.cpp => attach.cpp} | 55 ++++++++++++---------- .../commands/{attach-manager.hpp => attach.hpp} | 51 +++++++++++--------- libs/lxcpp/commands/command.hpp | 36 ++++++++++++++ libs/lxcpp/container-impl.cpp | 15 +++--- 4 files changed, 103 insertions(+), 54 deletions(-) rename libs/lxcpp/commands/{attach-manager.cpp => attach.cpp} (71%) rename libs/lxcpp/commands/{attach-manager.hpp => attach.hpp} (54%) create mode 100644 libs/lxcpp/commands/command.hpp diff --git a/libs/lxcpp/commands/attach-manager.cpp b/libs/lxcpp/commands/attach.cpp similarity index 71% rename from libs/lxcpp/commands/attach-manager.cpp rename to libs/lxcpp/commands/attach.cpp index 1a274d3..98a4599 100644 --- a/libs/lxcpp/commands/attach-manager.cpp +++ b/libs/lxcpp/commands/attach.cpp @@ -21,7 +21,7 @@ * @brief Implementation of attaching to a container */ -#include "lxcpp/commands/attach-manager.hpp" +#include "lxcpp/commands/attach.hpp" #include "lxcpp/exception.hpp" #include "lxcpp/process.hpp" #include "lxcpp/filesystem.hpp" @@ -69,7 +69,7 @@ void setupMountPoints() int execFunction(void* call) { try { - return (*static_cast(call))(); + return (*static_cast(call))(); } catch(...) { return -1; // Non-zero on failure } @@ -78,29 +78,35 @@ int execFunction(void* call) } // namespace -AttachManager::AttachManager(lxcpp::ContainerImpl& container) - : mContainer(container) +Attach::Attach(lxcpp::ContainerImpl& container, + Container::AttachCall& userCall, + const int capsToKeep, + const std::string& workDirInContainer, + const std::vector& envToKeep, + const std::vector>& envToSet) + : mContainer(container), + mUserCall(userCall), + mCapsToKeep(capsToKeep), + mWorkDirInContainer(workDirInContainer), + mEnvToKeep(envToKeep), + mEnvToSet(envToSet) { } -AttachManager::~AttachManager() +Attach::~Attach() { } -void AttachManager::attach(Container::AttachCall& userCall, - const int capsToKeep, - const std::string& workDirInContainer, - const std::vector& envToKeep, - const std::vector>& envToSet) +void Attach::execute() { // Channels for setup synchronization utils::Channel intermChannel; - Call call = std::bind(&AttachManager::child, - std::move(userCall), - capsToKeep, - std::move(envToKeep), - std::move(envToSet)); + Call call = std::bind(&Attach::child, + mUserCall, + mCapsToKeep, + mEnvToKeep, + mEnvToSet); const pid_t interPid = lxcpp::fork(); if (interPid > 0) { @@ -109,16 +115,16 @@ void AttachManager::attach(Container::AttachCall& userCall, intermChannel.shutdown(); } else { intermChannel.setRight(); - interm(intermChannel, workDirInContainer, call); + interm(intermChannel, call); intermChannel.shutdown(); ::_exit(0); } } -int AttachManager::child(const Container::AttachCall& call, - const int capsToKeep, - const std::vector& envToKeep, - const std::vector>& envToSet) +int Attach::child(const Container::AttachCall& call, + const int capsToKeep, + const std::vector& envToKeep, + const std::vector>& envToSet) { // Setup capabilities dropCapsFromBoundingExcept(capsToKeep); @@ -134,7 +140,7 @@ int AttachManager::child(const Container::AttachCall& call, return call(); } -void AttachManager::parent(utils::Channel& intermChannel, const pid_t interPid) +void Attach::parent(utils::Channel& intermChannel, const pid_t interPid) { // TODO: Setup cgroups etc const pid_t childPid = intermChannel.read(); @@ -144,15 +150,13 @@ void AttachManager::parent(utils::Channel& intermChannel, const pid_t interPid) lxcpp::waitpid(childPid); } -void AttachManager::interm(utils::Channel& intermChannel, - const std::string& workDirInContainer, - Call& call) +void Attach::interm(utils::Channel& intermChannel, Call& call) { lxcpp::setns(mContainer.getInitPid(), mContainer.getNamespaces()); // Change the current work directory // workDirInContainer is a path relative to the container's root - lxcpp::chdir(workDirInContainer); + lxcpp::chdir(mWorkDirInContainer); // PID namespace won't affect the returned pid // CLONE_PARENT: Child's PPID == Caller's PID @@ -160,7 +164,6 @@ void AttachManager::interm(utils::Channel& intermChannel, &call, CLONE_PARENT); intermChannel.write(childPid); - } } // namespace lxcpp diff --git a/libs/lxcpp/commands/attach-manager.hpp b/libs/lxcpp/commands/attach.hpp similarity index 54% rename from libs/lxcpp/commands/attach-manager.hpp rename to libs/lxcpp/commands/attach.hpp index f286564..342b613 100644 --- a/libs/lxcpp/commands/attach-manager.hpp +++ b/libs/lxcpp/commands/attach.hpp @@ -21,9 +21,10 @@ * @brief Implementation of attaching to a container */ -#ifndef LXCPP_ATTACH_MANAGER_HPP -#define LXCPP_ATTACH_MANAGER_HPP +#ifndef LXCPP_COMMANDS_ATTACH_HPP +#define LXCPP_COMMANDS_ATTACH_HPP +#include "lxcpp/commands/command.hpp" #include "lxcpp/container-impl.hpp" #include "utils/channel.hpp" @@ -31,31 +32,40 @@ namespace lxcpp { -class AttachManager final { +class Attach final: Command { public: typedef std::function Call; - AttachManager(lxcpp::ContainerImpl& container); - ~AttachManager(); - /** - * Runs the call in the container's context + * Runs call in the container's context + * + * Object attach should be used immediately after creation. + * It will not be stored for future use like most other commands. * - * @param call function to run inside container - * @param capsToKeep mask of the capabilities that shouldn't be dropped - * @param workDirInContainer Current Work Directory. Path relative to container's root - * @param envToKeep environment variables to keep in container - * @param envToSet environment variables to add/modify in container + * @param container container to which it attaches + * @param userCall user's function to run + * @param capsToKeep capabilities that will be kept + * @param workDirInContainer work directory set for the new process + * @param envToKeep environment variables that will be kept + * @param envToSet new environment variables that will be set */ - void attach(Container::AttachCall& call, - const int capsToKeep, - const std::string& workDirInContainer, - const std::vector& envToKeep, - const std::vector>& envToSet); + Attach(lxcpp::ContainerImpl& container, + Container::AttachCall& userCall, + const int capsToKeep, + const std::string& workDirInContainer, + const std::vector& envToKeep, + const std::vector>& envToSet); + ~Attach(); -private: + void execute(); +private: const lxcpp::ContainerImpl& mContainer; + const Container::AttachCall& mUserCall; + const int mCapsToKeep; + const std::string& mWorkDirInContainer; + const std::vector& mEnvToKeep; + const std::vector>& mEnvToSet; // Methods for different stages of setting up the attachment static int child(const Container::AttachCall& call, @@ -67,10 +77,9 @@ private: const pid_t pid); void interm(utils::Channel& intermChannel, - const std::string& workDirInContainer, - Container::AttachCall& call); + Call& call); }; } // namespace lxcpp -#endif // LXCPP_ATTACH_MANAGER_HPP \ No newline at end of file +#endif // LXCPP_COMMANDS_ATTACH_HPP \ No newline at end of file diff --git a/libs/lxcpp/commands/command.hpp b/libs/lxcpp/commands/command.hpp new file mode 100644 index 0000000..cd301ee --- /dev/null +++ b/libs/lxcpp/commands/command.hpp @@ -0,0 +1,36 @@ +/* + * Copyright (C) 2015 Samsung Electronics Co., Ltd All Rights Reserved + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License version 2.1 as published by the Free Software Foundation. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +/** + * @file + * @author Jan Olszak (j.olszak@samsung.com) + * @brief Command interface definition + */ + +#ifndef LXCPP_COMMANDS_COMMAND_HPP +#define LXCPP_COMMANDS_COMMAND_HPP + +namespace lxcpp { + +class Command { +public: + virtual void execute() = 0; +}; + +} // namespace lxcpp + +#endif // LXCPP_COMMANDS_COMMAND_HPP \ No newline at end of file diff --git a/libs/lxcpp/container-impl.cpp b/libs/lxcpp/container-impl.cpp index 0d8d5b1..7189bc7 100644 --- a/libs/lxcpp/container-impl.cpp +++ b/libs/lxcpp/container-impl.cpp @@ -27,7 +27,7 @@ #include "lxcpp/filesystem.hpp" #include "lxcpp/namespace.hpp" #include "lxcpp/capability.hpp" -#include "lxcpp/commands/attach-manager.hpp" +#include "lxcpp/commands/attach.hpp" #include "utils/exception.hpp" @@ -107,13 +107,14 @@ std::string ContainerImpl::getRootPath() void ContainerImpl::attach(Container::AttachCall& call, const std::string& cwdInContainer) { - AttachManager attachManager(*this); + Attach attach(*this, + call, + /*capsToKeep*/ 0, + cwdInContainer, + /*envToKeep*/ {}, + /*envInContainer*/ {{"container","lxcpp"}}); // TODO: Env variables should agree with the ones already in the container - attachManager.attach(call, - /*capsToKeep*/ 0, - cwdInContainer, - /*envToKeep*/ {}, - /*envInContainer*/{{"container","lxcpp"}} ); + attach.execute(); } const std::vector& ContainerImpl::getNamespaces() const -- 2.7.4