From c2b1654c11313b9eec366239bc5108df7a5a051e Mon Sep 17 00:00:00 2001 From: Nikita Ioffe Date: Thu, 20 Oct 2022 14:14:39 +0100 Subject: [PATCH] init: skip cgroup/task_profiles configuration if cgroups are disabled We are planning to remove cgroups from the Micrdroid kernel, since the entire VM belongs exclusively to a single owner, and is in the control of the cgroups on the host side. This patch expoxes CgroupAvailable API from libprocessgroup, and changes init to query the CgroupAvailable API before doing any cgroups/task_profiles related work. Bug: 239367015 Test: run MicrodroidDemoApp Test: atest --test-mapping packages/modules/Virtualization:avf-presubmit Change-Id: I82787141cd2a7f9309a4e9b24acbd92ca21c145b --- init/init.cpp | 4 +++ init/service.cpp | 34 +++++++++++-------- init/service_utils.cpp | 9 +++++ .../include/processgroup/processgroup.h | 1 + libprocessgroup/processgroup.cpp | 5 +++ 5 files changed, 38 insertions(+), 15 deletions(-) diff --git a/init/init.cpp b/init/init.cpp index cd0ee58ec..2d9fbbf3e 100644 --- a/init/init.cpp +++ b/init/init.cpp @@ -662,6 +662,10 @@ static Result wait_for_coldboot_done_action(const BuiltinArguments& args) } static Result SetupCgroupsAction(const BuiltinArguments&) { + if (!CgroupsAvailable()) { + LOG(INFO) << "Cgroups support in kernel is not enabled"; + return {}; + } // Have to create using make_dir function // for appropriate sepolicy to be set for it make_dir(android::base::Dirname(CGROUPS_RC_PATH), 0711); diff --git a/init/service.cpp b/init/service.cpp index a6330484a..24fcdce75 100644 --- a/init/service.cpp +++ b/init/service.cpp @@ -682,24 +682,28 @@ Result Service::Start() { start_order_ = next_start_order_++; process_cgroup_empty_ = false; - bool use_memcg = swappiness_ != -1 || soft_limit_in_bytes_ != -1 || limit_in_bytes_ != -1 || - limit_percent_ != -1 || !limit_property_.empty(); - errno = -createProcessGroup(proc_attr_.uid, pid_, use_memcg); - if (errno != 0) { - if (char byte = 0; write((*pipefd)[1], &byte, 1) < 0) { - return ErrnoError() << "sending notification failed"; + if (CgroupsAvailable()) { + bool use_memcg = swappiness_ != -1 || soft_limit_in_bytes_ != -1 || limit_in_bytes_ != -1 || + limit_percent_ != -1 || !limit_property_.empty(); + errno = -createProcessGroup(proc_attr_.uid, pid_, use_memcg); + if (errno != 0) { + if (char byte = 0; write((*pipefd)[1], &byte, 1) < 0) { + return ErrnoError() << "sending notification failed"; + } + return Error() << "createProcessGroup(" << proc_attr_.uid << ", " << pid_ + << ") failed for service '" << name_ << "'"; } - return Error() << "createProcessGroup(" << proc_attr_.uid << ", " << pid_ - << ") failed for service '" << name_ << "'"; - } - // When the blkio controller is mounted in the v1 hierarchy, NormalIoPriority is - // the default (/dev/blkio). When the blkio controller is mounted in the v2 hierarchy, the - // NormalIoPriority profile has to be applied explicitly. - SetProcessProfiles(proc_attr_.uid, pid_, {"NormalIoPriority"}); + // When the blkio controller is mounted in the v1 hierarchy, NormalIoPriority is + // the default (/dev/blkio). When the blkio controller is mounted in the v2 hierarchy, the + // NormalIoPriority profile has to be applied explicitly. + SetProcessProfiles(proc_attr_.uid, pid_, {"NormalIoPriority"}); - if (use_memcg) { - ConfigureMemcg(); + if (use_memcg) { + ConfigureMemcg(); + } + } else { + process_cgroup_empty_ = true; } if (oom_score_adjust_ != DEFAULT_OOM_SCORE_ADJUST) { diff --git a/init/service_utils.cpp b/init/service_utils.cpp index d19f5eef5..a14969e98 100644 --- a/init/service_utils.cpp +++ b/init/service_utils.cpp @@ -280,6 +280,15 @@ Result SetProcessAttributes(const ProcessAttributes& attr) { } Result WritePidToFiles(std::vector* files) { + if (files->empty()) { + // No files to write pid to, exit early. + return {}; + } + + if (!CgroupsAvailable()) { + return Error() << "cgroups are not available"; + } + // See if there were "writepid" instructions to write to files under cpuset path. std::string cpuset_path; if (CgroupGetControllerPath("cpuset", &cpuset_path)) { diff --git a/libprocessgroup/include/processgroup/processgroup.h b/libprocessgroup/include/processgroup/processgroup.h index 45a723f74..9b2d77567 100644 --- a/libprocessgroup/include/processgroup/processgroup.h +++ b/libprocessgroup/include/processgroup/processgroup.h @@ -28,6 +28,7 @@ __BEGIN_DECLS static constexpr const char* CGROUPV2_CONTROLLER_NAME = "cgroup2"; +bool CgroupsAvailable(); bool CgroupGetControllerPath(const std::string& cgroup_name, std::string* path); bool CgroupGetControllerFromPath(const std::string& path, std::string* cgroup_name); bool CgroupGetAttributePath(const std::string& attr_name, std::string* path); diff --git a/libprocessgroup/processgroup.cpp b/libprocessgroup/processgroup.cpp index bdda1020c..3fac373cb 100644 --- a/libprocessgroup/processgroup.cpp +++ b/libprocessgroup/processgroup.cpp @@ -55,6 +55,11 @@ using namespace std::chrono_literals; #define PROCESSGROUP_CGROUP_PROCS_FILE "/cgroup.procs" +bool CgroupsAvailable() { + static bool cgroups_available = access("/proc/cgroups", F_OK) == 0; + return cgroups_available; +} + bool CgroupGetControllerPath(const std::string& cgroup_name, std::string* path) { auto controller = CgroupMap::GetInstance().FindController(cgroup_name);