libprocessgroup: Support memcg v1 per-app with PRODUCT_CGROUP_V2_SYS_APP_ISOLATION_ENABLED
We are enabling PRODUCT_CGROUP_V2_SYS_APP_ISOLATION_ENABLED by default
and also temporarily retaining support for overriding the new memcg v2
default back to v1. That means the default
PRODUCT_CGROUP_V2_SYS_APP_ISOLATION_ENABLED must work correctly with v1
per-application memcg paths, which is not currently the case. This
change uses knowledge about whether paths being generated are for a v1
cgroup or a v2 cgroup so that the common ConvertUid{Pid}ToPath functions
can continue to be used for both v1 and v2 cases.
Memcg v1 support will eventually be removed, so this change can be
reverted when that happens.
Test: boot cf_gwear_x86-trunk_staging-userdebug with
PRODUCT_CGROUP_V2_SYS_APP_ISOLATION_ENABLED = true.
cf_gwear_x86-trunk_staging-userdebug sets ro.config.low_ram
causing v1 per-app memcgs to be used.
Bug: 377579705
Change-Id: Iec26c02fd261bdec80a7e49fce4dc207d1996b1b
diff --git a/libprocessgroup/processgroup.cpp b/libprocessgroup/processgroup.cpp
index 9522159..f83e042 100644
--- a/libprocessgroup/processgroup.cpp
+++ b/libprocessgroup/processgroup.cpp
@@ -85,7 +85,8 @@
CgroupGetControllerPath(CGROUPV2_HIERARCHY_NAME, &cg_kill);
// cgroup.kill is not on the root cgroup, so check a non-root cgroup that should always
// exist
- cg_kill = ConvertUidToPath(cg_kill.c_str(), AID_ROOT) + '/' + PROCESSGROUP_CGROUP_KILL_FILE;
+ cg_kill = ConvertUidToPath(cg_kill.c_str(), AID_ROOT, true) + '/' +
+ PROCESSGROUP_CGROUP_KILL_FILE;
cgroup_kill_available = access(cg_kill.c_str(), F_OK) == 0;
});
@@ -224,14 +225,14 @@
false);
}
-static int RemoveCgroup(const char* cgroup, uid_t uid, pid_t pid) {
- auto path = ConvertUidPidToPath(cgroup, uid, pid);
+static int RemoveCgroup(const char* cgroup, uid_t uid, pid_t pid, bool v2_path) {
+ auto path = ConvertUidPidToPath(cgroup, uid, pid, v2_path);
int ret = TEMP_FAILURE_RETRY(rmdir(path.c_str()));
if (!ret && uid >= AID_ISOLATED_START && uid <= AID_ISOLATED_END) {
// Isolated UIDs are unlikely to be reused soon after removal,
// so free up the kernel resources for the UID level cgroup.
- path = ConvertUidToPath(cgroup, uid);
+ path = ConvertUidToPath(cgroup, uid, v2_path);
ret = TEMP_FAILURE_RETRY(rmdir(path.c_str()));
}
@@ -368,7 +369,7 @@
if (CgroupsAvailable()) {
std::string hierarchy_root_path, cgroup_v2_path;
CgroupGetControllerPath(CGROUPV2_HIERARCHY_NAME, &hierarchy_root_path);
- cgroup_v2_path = ConvertUidPidToPath(hierarchy_root_path.c_str(), uid, initialPid);
+ cgroup_v2_path = ConvertUidPidToPath(hierarchy_root_path.c_str(), uid, initialPid, true);
if (signal == SIGKILL && CgroupKillAvailable()) {
LOG(VERBOSE) << "Using " << PROCESSGROUP_CGROUP_KILL_FILE << " to SIGKILL "
@@ -539,7 +540,7 @@
CgroupGetControllerPath(CGROUPV2_HIERARCHY_NAME, &hierarchy_root_path);
const std::string cgroup_v2_path =
- ConvertUidPidToPath(hierarchy_root_path.c_str(), uid, initialPid);
+ ConvertUidPidToPath(hierarchy_root_path.c_str(), uid, initialPid, true);
const std::string eventsfile = cgroup_v2_path + '/' + PROCESSGROUP_CGROUP_EVENTS_FILE;
android::base::unique_fd events_fd(open(eventsfile.c_str(), O_RDONLY));
@@ -605,7 +606,7 @@
<< " after " << kill_duration.count() << " ms";
}
- ret = RemoveCgroup(hierarchy_root_path.c_str(), uid, initialPid);
+ ret = RemoveCgroup(hierarchy_root_path.c_str(), uid, initialPid, true);
if (ret)
PLOG(ERROR) << "Unable to remove cgroup " << cgroup_v2_path;
else
@@ -616,9 +617,9 @@
// memcg v2.
std::string memcg_apps_path;
if (CgroupGetMemcgAppsPath(&memcg_apps_path) &&
- (ret = RemoveCgroup(memcg_apps_path.c_str(), uid, initialPid)) < 0) {
+ (ret = RemoveCgroup(memcg_apps_path.c_str(), uid, initialPid, false)) < 0) {
const auto memcg_v1_cgroup_path =
- ConvertUidPidToPath(memcg_apps_path.c_str(), uid, initialPid);
+ ConvertUidPidToPath(memcg_apps_path.c_str(), uid, initialPid, false);
PLOG(ERROR) << "Unable to remove memcg v1 cgroup " << memcg_v1_cgroup_path;
}
}
@@ -640,7 +641,7 @@
static int createProcessGroupInternal(uid_t uid, pid_t initialPid, std::string cgroup,
bool activate_controllers) {
- auto uid_path = ConvertUidToPath(cgroup.c_str(), uid);
+ auto uid_path = ConvertUidToPath(cgroup.c_str(), uid, activate_controllers);
struct stat cgroup_stat;
mode_t cgroup_mode = 0750;
@@ -667,7 +668,7 @@
}
}
- auto uid_pid_path = ConvertUidPidToPath(cgroup.c_str(), uid, initialPid);
+ auto uid_pid_path = ConvertUidPidToPath(cgroup.c_str(), uid, initialPid, activate_controllers);
if (!MkdirAndChown(uid_pid_path, cgroup_mode, cgroup_uid, cgroup_gid)) {
PLOG(ERROR) << "Failed to make and chown " << uid_pid_path;
diff --git a/libprocessgroup/task_profiles.cpp b/libprocessgroup/task_profiles.cpp
index dc6c8c0..c03c257 100644
--- a/libprocessgroup/task_profiles.cpp
+++ b/libprocessgroup/task_profiles.cpp
@@ -150,8 +150,8 @@
return uid < AID_APP_START;
}
-std::string ConvertUidToPath(const char* root_cgroup_path, uid_t uid) {
- if (android::libprocessgroup_flags::cgroup_v2_sys_app_isolation()) {
+std::string ConvertUidToPath(const char* root_cgroup_path, uid_t uid, bool v2_path) {
+ if (android::libprocessgroup_flags::cgroup_v2_sys_app_isolation() && v2_path) {
if (isSystemApp(uid))
return StringPrintf("%s/system/uid_%u", root_cgroup_path, uid);
else
@@ -160,14 +160,14 @@
return StringPrintf("%s/uid_%u", root_cgroup_path, uid);
}
-std::string ConvertUidPidToPath(const char* root_cgroup_path, uid_t uid, pid_t pid) {
- const std::string uid_path = ConvertUidToPath(root_cgroup_path, uid);
+std::string ConvertUidPidToPath(const char* root_cgroup_path, uid_t uid, pid_t pid, bool v2_path) {
+ const std::string uid_path = ConvertUidToPath(root_cgroup_path, uid, v2_path);
return StringPrintf("%s/pid_%d", uid_path.c_str(), pid);
}
bool ProfileAttribute::GetPathForProcess(uid_t uid, pid_t pid, std::string* path) const {
if (controller()->version() == 2) {
- const std::string cgroup_path = ConvertUidPidToPath(controller()->path(), uid, pid);
+ const std::string cgroup_path = ConvertUidPidToPath(controller()->path(), uid, pid, true);
*path = cgroup_path + "/" + file_name();
return true;
}
@@ -199,7 +199,7 @@
return true;
}
- const std::string cgroup_path = ConvertUidToPath(controller()->path(), uid);
+ const std::string cgroup_path = ConvertUidToPath(controller()->path(), uid, true);
*path = cgroup_path + "/" + file_name();
return true;
}
diff --git a/libprocessgroup/task_profiles.h b/libprocessgroup/task_profiles.h
index d0b5043..b1d6115 100644
--- a/libprocessgroup/task_profiles.h
+++ b/libprocessgroup/task_profiles.h
@@ -258,5 +258,5 @@
std::map<std::string, std::unique_ptr<IProfileAttribute>, std::less<>> attributes_;
};
-std::string ConvertUidToPath(const char* root_cgroup_path, uid_t uid);
-std::string ConvertUidPidToPath(const char* root_cgroup_path, uid_t uid, pid_t pid);
+std::string ConvertUidToPath(const char* root_cgroup_path, uid_t uid, bool v2_path);
+std::string ConvertUidPidToPath(const char* root_cgroup_path, uid_t uid, pid_t pid, bool v2_path);