提交 d364232d 编写于 作者: J Jing Xiangfeng 提交者: Zheng Zengkai

memcg: Add static key for memcg priority

hulk inclusion
category: feature
bugzilla: https://gitee.com/openeuler/kernel/issues/I3ZN3O
CVE: NA

--------------------------------------

This patch adds a default-false static key to disable memcg priority
feature. If you want to enable it by writing 1:

echo 1 > /proc/sys/vm/memcg_qos_enable
Signed-off-by: NJing Xiangfeng <jingxiangfeng@huawei.com>
Reviewed-by: NLiu Shixin <liushixin2@huawei.com>
Signed-off-by: NZheng Zengkai <zhengzengkai@huawei.com>
上级 c74e4299
...@@ -342,9 +342,16 @@ struct mem_cgroup { ...@@ -342,9 +342,16 @@ struct mem_cgroup {
}; };
#ifdef CONFIG_MEMCG_QOS #ifdef CONFIG_MEMCG_QOS
#define ENABLE_MEMCG_QOS 1
#define DISABLE_MEMCG_QOS 0
extern int sysctl_memcg_qos_stat;
DECLARE_STATIC_KEY_FALSE(memcg_qos_stat_key);
bool memcg_low_priority_scan_tasks(int (*)(struct task_struct *, void *), bool memcg_low_priority_scan_tasks(int (*)(struct task_struct *, void *),
void *); void *);
void memcg_print_bad_task(void *arg, int ret); void memcg_print_bad_task(void *arg, int ret);
extern int sysctl_memcg_qos_handler(struct ctl_table *table,
int write, void __user *buffer, size_t *length, loff_t *ppos);
#endif #endif
/* /*
......
...@@ -2825,6 +2825,17 @@ static struct ctl_table vm_table[] = { ...@@ -2825,6 +2825,17 @@ static struct ctl_table vm_table[] = {
.mode = 0644, .mode = 0644,
.proc_handler = hugetlb_overcommit_handler, .proc_handler = hugetlb_overcommit_handler,
}, },
#endif
#ifdef CONFIG_MEMCG_QOS
{
.procname = "memcg_qos_enable",
.data = &sysctl_memcg_qos_stat,
.maxlen = sizeof(int),
.mode = 0644,
.proc_handler = sysctl_memcg_qos_handler,
.extra1 = SYSCTL_ZERO,
.extra2 = SYSCTL_ONE,
},
#endif #endif
{ {
.procname = "lowmem_reserve_ratio", .procname = "lowmem_reserve_ratio",
......
...@@ -3957,10 +3957,16 @@ static int mem_cgroup_move_charge_write(struct cgroup_subsys_state *css, ...@@ -3957,10 +3957,16 @@ static int mem_cgroup_move_charge_write(struct cgroup_subsys_state *css,
#endif #endif
#ifdef CONFIG_MEMCG_QOS #ifdef CONFIG_MEMCG_QOS
int sysctl_memcg_qos_stat = DISABLE_MEMCG_QOS;
DEFINE_STATIC_KEY_FALSE(memcg_qos_stat_key);
static void memcg_qos_init(struct mem_cgroup *memcg) static void memcg_qos_init(struct mem_cgroup *memcg)
{ {
struct mem_cgroup *parent = parent_mem_cgroup(memcg); struct mem_cgroup *parent = parent_mem_cgroup(memcg);
if (!static_branch_likely(&memcg_qos_stat_key))
return;
if (!parent) if (!parent)
return; return;
...@@ -3971,6 +3977,9 @@ static void memcg_qos_init(struct mem_cgroup *memcg) ...@@ -3971,6 +3977,9 @@ static void memcg_qos_init(struct mem_cgroup *memcg)
static s64 memcg_qos_read(struct cgroup_subsys_state *css, static s64 memcg_qos_read(struct cgroup_subsys_state *css,
struct cftype *cft) struct cftype *cft)
{ {
if (!static_branch_likely(&memcg_qos_stat_key))
return 0;
return mem_cgroup_from_css(css)->memcg_priority; return mem_cgroup_from_css(css)->memcg_priority;
} }
...@@ -3979,6 +3988,9 @@ static int memcg_qos_write(struct cgroup_subsys_state *css, ...@@ -3979,6 +3988,9 @@ static int memcg_qos_write(struct cgroup_subsys_state *css,
{ {
struct mem_cgroup *memcg = mem_cgroup_from_css(css); struct mem_cgroup *memcg = mem_cgroup_from_css(css);
if (!static_branch_likely(&memcg_qos_stat_key))
return -EACCES;
if (val >= 0) if (val >= 0)
memcg->memcg_priority = 0; memcg->memcg_priority = 0;
else else
...@@ -4022,6 +4034,8 @@ bool memcg_low_priority_scan_tasks(int (*fn)(struct task_struct *, void *), ...@@ -4022,6 +4034,8 @@ bool memcg_low_priority_scan_tasks(int (*fn)(struct task_struct *, void *),
int ret = 0; int ret = 0;
bool retry = true; bool retry = true;
if (!static_branch_likely(&memcg_qos_stat_key))
return false;
retry: retry:
max = memcg_find_max_usage(last); max = memcg_find_max_usage(last);
if (!max) if (!max)
...@@ -4058,6 +4072,9 @@ void memcg_print_bad_task(void *arg, int ret) ...@@ -4058,6 +4072,9 @@ void memcg_print_bad_task(void *arg, int ret)
{ {
struct oom_control *oc = arg; struct oom_control *oc = arg;
if (!static_branch_likely(&memcg_qos_stat_key))
return;
if (!ret && oc->chosen) { if (!ret && oc->chosen) {
struct mem_cgroup *memcg; struct mem_cgroup *memcg;
...@@ -4067,6 +4084,41 @@ void memcg_print_bad_task(void *arg, int ret) ...@@ -4067,6 +4084,41 @@ void memcg_print_bad_task(void *arg, int ret)
oc->chosen->pid, oc->chosen->comm); oc->chosen->pid, oc->chosen->comm);
} }
} }
static void memcg_qos_reset(void)
{
struct mem_cgroup *iter;
struct cgroup_subsys_state *css;
rcu_read_lock();
css_for_each_descendant_pre(css, &root_mem_cgroup->css) {
iter = mem_cgroup_from_css(css);
iter->memcg_priority = 0;
}
rcu_read_unlock();
}
int sysctl_memcg_qos_handler(struct ctl_table *table, int write,
void __user *buffer, size_t *length, loff_t *ppos)
{
int ret;
ret = proc_dointvec_minmax(table, write, buffer, length, ppos);
if (ret)
return ret;
if (write) {
if (sysctl_memcg_qos_stat == ENABLE_MEMCG_QOS) {
static_branch_enable(&memcg_qos_stat_key);
pr_info("enable memcg priority.\n");
} else {
static_branch_disable(&memcg_qos_stat_key);
memcg_qos_reset();
pr_info("disable memcg priority.\n");
}
}
return ret;
}
#endif #endif
#ifdef CONFIG_NUMA #ifdef CONFIG_NUMA
......
...@@ -316,6 +316,8 @@ static bool oom_next_task(struct task_struct *task, struct oom_control *oc, ...@@ -316,6 +316,8 @@ static bool oom_next_task(struct task_struct *task, struct oom_control *oc,
struct mem_cgroup *cur_memcg; struct mem_cgroup *cur_memcg;
struct mem_cgroup *oc_memcg; struct mem_cgroup *oc_memcg;
if (!static_branch_likely(&memcg_qos_stat_key))
return !points || points < oc->chosen_points;
if (!points) if (!points)
return true; return true;
...@@ -341,10 +343,7 @@ static bool oom_next_task(struct task_struct *task, struct oom_control *oc, ...@@ -341,10 +343,7 @@ static bool oom_next_task(struct task_struct *task, struct oom_control *oc,
static inline bool oom_next_task(struct task_struct *task, static inline bool oom_next_task(struct task_struct *task,
struct oom_control *oc, unsigned long points) struct oom_control *oc, unsigned long points)
{ {
if (!points || points < oc->chosen_points) return !points || points < oc->chosen_points;
return true;
return false;
} }
#endif #endif
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册