Received: by 2002:ac0:a594:0:0:0:0:0 with SMTP id m20-v6csp209219imm; Mon, 21 May 2018 04:56:08 -0700 (PDT) X-Google-Smtp-Source: AB8JxZo6sfLFm6jbBiA/UOOCdQ56QtbKn4WrUJG14Xc5Gn6cN++8kSM2lrqK0M9FtIdMrdKIIR5v X-Received: by 2002:a63:41c4:: with SMTP id o187-v6mr15118723pga.7.1526903768630; Mon, 21 May 2018 04:56:08 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1526903768; cv=none; d=google.com; s=arc-20160816; b=vaDaWBdOf1mPHNQZziw5odPhqXhw8FzfKRcpO3hEq3yuqtfx9qmEkMbI9F5ealTTqE tKMSRaLfCIp76SUBasTCETgYtyoFvl5AZxA29u5OB+QzTgfim8+W4/ibSLhtbB54Iwwu tvxP18B2DFgz7mIcJG45KjUlkVx3KzCi6+kohlky2qVmSVadYFhpii8jS92P2c82sNUE 4xAtpIdO9dIZS3QbarnF19r4+6InrzccqZi2j4oOtUDZk3vgmFMueC3ZmtmK6w4OluyE 3Yvxfuu+cd+q+XeQWtCVVWGd2OU9Q+V5N29SzWqlY0mbDeMJSfmI4Zc7tlgGHmRpQtOo 5JMQ== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:sender:user-agent:in-reply-to :content-disposition:mime-version:references:message-id:subject:cc :to:from:date:arc-authentication-results; bh=vx9/CU05lRRJV9xTjZrUfkBwMST8SilFiCjCgSiOR2s=; b=GF509ZkvoB/qchcxD0mscZHNJbBUuCegVL9IZwe6vJBvyKOjFn0UMlgIqU9ctDJof7 u4n0FSMGIh1KuyigL0ygqhMQzROvdwcpSuxESTXLod0pBvpw4cyyW1jX0EdDGUi93VWC hC/39Y5M2dyBpDxVj/VYkPvKzerev0Fs7F07L6Ygp5VqLcm4qemslzDLu2Xrt3PZyTYf YZlkJF3VEILsrT1ZHcNUDXnSY/nFEGNpLyGFos26rcv8vDzdROasaOalVB1/SSVlSARl 58MrMVcqFM/Tm1t0bdHH+3EEqmCxspTN9fNgIwcBkXFig1k50KBEOqb7FKXRwyIT3ait Ms7A== ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org Return-Path: Received: from vger.kernel.org (vger.kernel.org. [209.132.180.67]) by mx.google.com with ESMTP id d11-v6si14396460pfh.131.2018.05.21.04.55.54; Mon, 21 May 2018 04:56:08 -0700 (PDT) Received-SPF: pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) client-ip=209.132.180.67; Authentication-Results: mx.google.com; spf=pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1752813AbeEULzh (ORCPT + 99 others); Mon, 21 May 2018 07:55:37 -0400 Received: from usa-sjc-mx-foss1.foss.arm.com ([217.140.101.70]:48194 "EHLO foss.arm.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1751077AbeEULze (ORCPT ); Mon, 21 May 2018 07:55:34 -0400 Received: from usa-sjc-imap-foss1.foss.arm.com (unknown [10.72.51.249]) by usa-sjc-mx-foss1.foss.arm.com (Postfix) with ESMTP id DE06680D; Mon, 21 May 2018 04:55:33 -0700 (PDT) Received: from e110439-lin (e110439-lin.cambridge.arm.com [10.1.210.68]) by usa-sjc-imap-foss1.foss.arm.com (Postfix) with ESMTPSA id 3F2AB3F25D; Mon, 21 May 2018 04:55:31 -0700 (PDT) Date: Mon, 21 May 2018 12:55:28 +0100 From: Patrick Bellasi To: Waiman Long Cc: Tejun Heo , Li Zefan , Johannes Weiner , Peter Zijlstra , Ingo Molnar , cgroups@vger.kernel.org, linux-kernel@vger.kernel.org, linux-doc@vger.kernel.org, kernel-team@fb.com, pjt@google.com, luto@amacapital.net, Mike Galbraith , torvalds@linux-foundation.org, Roman Gushchin , Juri Lelli Subject: Re: [PATCH v8 1/6] cpuset: Enable cpuset controller in default hierarchy Message-ID: <20180521115528.GR30654@e110439-lin> References: <1526590545-3350-1-git-send-email-longman@redhat.com> <1526590545-3350-2-git-send-email-longman@redhat.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1526590545-3350-2-git-send-email-longman@redhat.com> User-Agent: Mutt/1.5.24 (2015-08-30) Sender: linux-kernel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Hi Waiman! I've started looking at the possibility to move Android to use cgroups v2 and the availability of the cpuset controller makes this even more promising. I'll try to give a run to this series on Android, meanwhile I have some (hopefully not too much dummy) questions below. On 17-May 16:55, Waiman Long wrote: > Given the fact that thread mode had been merged into 4.14, it is now > time to enable cpuset to be used in the default hierarchy (cgroup v2) > as it is clearly threaded. > > The cpuset controller had experienced feature creep since its > introduction more than a decade ago. Besides the core cpus and mems > control files to limit cpus and memory nodes, there are a bunch of > additional features that can be controlled from the userspace. Some of > the features are of doubtful usefulness and may not be actively used. > > This patch enables cpuset controller in the default hierarchy with > a minimal set of features, namely just the cpus and mems and their > effective_* counterparts. We can certainly add more features to the > default hierarchy in the future if there is a real user need for them > later on. > > Alternatively, with the unified hiearachy, it may make more sense > to move some of those additional cpuset features, if desired, to > memory controller or may be to the cpu controller instead of staying > with cpuset. > > Signed-off-by: Waiman Long > --- > Documentation/cgroup-v2.txt | 90 ++++++++++++++++++++++++++++++++++++++++++--- > kernel/cgroup/cpuset.c | 48 ++++++++++++++++++++++-- > 2 files changed, 130 insertions(+), 8 deletions(-) > > diff --git a/Documentation/cgroup-v2.txt b/Documentation/cgroup-v2.txt > index 74cdeae..cf7bac6 100644 > --- a/Documentation/cgroup-v2.txt > +++ b/Documentation/cgroup-v2.txt > @@ -53,11 +53,13 @@ v1 is available under Documentation/cgroup-v1/. > 5-3-2. Writeback > 5-4. PID > 5-4-1. PID Interface Files > - 5-5. Device > - 5-6. RDMA > - 5-6-1. RDMA Interface Files > - 5-7. Misc > - 5-7-1. perf_event > + 5-5. Cpuset > + 5.5-1. Cpuset Interface Files > + 5-6. Device > + 5-7. RDMA > + 5-7-1. RDMA Interface Files > + 5-8. Misc > + 5-8-1. perf_event > 5-N. Non-normative information > 5-N-1. CPU controller root cgroup process behaviour > 5-N-2. IO controller root cgroup process behaviour > @@ -1435,6 +1437,84 @@ through fork() or clone(). These will return -EAGAIN if the creation > of a new process would cause a cgroup policy to be violated. > > > +Cpuset > +------ > + > +The "cpuset" controller provides a mechanism for constraining > +the CPU and memory node placement of tasks to only the resources > +specified in the cpuset interface files in a task's current cgroup. > +This is especially valuable on large NUMA systems where placing jobs > +on properly sized subsets of the systems with careful processor and > +memory placement to reduce cross-node memory access and contention > +can improve overall system performance. Another quite important use-case for cpuset is Android, where they are actively used to do both power-saving as well as performance tunings. For example, depending on the status of an application, its threads can be allowed to run on all available CPUS (e.g. foreground apps) or be restricted only on few energy efficient CPUs (e.g. backgroud apps). Since here we are at "rewriting" cpusets for v2, I think it's important to keep this mobile world scenario into consideration. For example, in this context, we are looking at the possibility to update/tune cpuset.cpus with a relatively high rate, i.e. tens of times per second. Not sure that's the same update rate usually required for the large NUMA systems you cite above. However, in this case it's quite important to have really small overheads for these operations. > + > +The "cpuset" controller is hierarchical. That means the controller > +cannot use CPUs or memory nodes not allowed in its parent. > + > + > +Cpuset Interface Files > +~~~~~~~~~~~~~~~~~~~~~~ > + > + cpuset.cpus > + A read-write multiple values file which exists on non-root > + cpuset-enabled cgroups. > + > + It lists the CPUs allowed to be used by tasks within this > + cgroup. The CPU numbers are comma-separated numbers or > + ranges. For example: > + > + # cat cpuset.cpus > + 0-4,6,8-10 > + > + An empty value indicates that the cgroup is using the same > + setting as the nearest cgroup ancestor with a non-empty > + "cpuset.cpus" or all the available CPUs if none is found. Does that means that we can move tasks into a newly created group for which we have not yet configured this value? AFAIK, that's a different behavior wrt v1... and I like it better. > + > + The value of "cpuset.cpus" stays constant until the next update > + and won't be affected by any CPU hotplug events. This also sounds interesting, does it means that we use the cpuset.cpus mask to restrict online CPUs, whatever they are? I'll have a better look at the code, but my understanding of v1 is that we spent a lot of effort to keep task cpu-affinity masks aligned with the cpuset in which they live, and we do something similar at each HP event, which ultimately generates a lot of overheads in systems where: you have many HP events and/or cpuset.cpus change quite frequently. I hope to find some better behavior in this series. > + > + cpuset.cpus.effective > + A read-only multiple values file which exists on non-root > + cpuset-enabled cgroups. > + > + It lists the onlined CPUs that are actually allowed to be > + used by tasks within the current cgroup. If "cpuset.cpus" > + is empty, it shows all the CPUs from the parent cgroup that > + will be available to be used by this cgroup. Otherwise, it is > + a subset of "cpuset.cpus". Its value will be affected by CPU > + hotplug events. This looks similar to v1, isn't it? > + > + cpuset.mems > + A read-write multiple values file which exists on non-root > + cpuset-enabled cgroups. > + > + It lists the memory nodes allowed to be used by tasks within > + this cgroup. The memory node numbers are comma-separated > + numbers or ranges. For example: > + > + # cat cpuset.mems > + 0-1,3 > + > + An empty value indicates that the cgroup is using the same > + setting as the nearest cgroup ancestor with a non-empty > + "cpuset.mems" or all the available memory nodes if none > + is found. > + > + The value of "cpuset.mems" stays constant until the next update > + and won't be affected by any memory nodes hotplug events. > + > + cpuset.mems.effective > + A read-only multiple values file which exists on non-root > + cpuset-enabled cgroups. > + > + It lists the onlined memory nodes that are actually allowed to > + be used by tasks within the current cgroup. If "cpuset.mems" > + is empty, it shows all the memory nodes from the parent cgroup > + that will be available to be used by this cgroup. Otherwise, > + it is a subset of "cpuset.mems". Its value will be affected > + by memory nodes hotplug events. > + > + > Device controller > ----------------- > > diff --git a/kernel/cgroup/cpuset.c b/kernel/cgroup/cpuset.c > index b42037e..419b758 100644 > --- a/kernel/cgroup/cpuset.c > +++ b/kernel/cgroup/cpuset.c > @@ -1823,12 +1823,11 @@ static s64 cpuset_read_s64(struct cgroup_subsys_state *css, struct cftype *cft) > return 0; > } > > - > /* > * for the common functions, 'private' gives the type of file > */ > > -static struct cftype files[] = { > +static struct cftype legacy_files[] = { > { > .name = "cpus", > .seq_show = cpuset_common_seq_show, > @@ -1931,6 +1930,47 @@ static s64 cpuset_read_s64(struct cgroup_subsys_state *css, struct cftype *cft) > }; > > /* > + * This is currently a minimal set for the default hierarchy. It can be > + * expanded later on by migrating more features and control files from v1. > + */ > +static struct cftype dfl_files[] = { > + { > + .name = "cpus", > + .seq_show = cpuset_common_seq_show, > + .write = cpuset_write_resmask, > + .max_write_len = (100U + 6 * NR_CPUS), > + .private = FILE_CPULIST, > + .flags = CFTYPE_NOT_ON_ROOT, > + }, > + > + { > + .name = "mems", > + .seq_show = cpuset_common_seq_show, > + .write = cpuset_write_resmask, > + .max_write_len = (100U + 6 * MAX_NUMNODES), > + .private = FILE_MEMLIST, > + .flags = CFTYPE_NOT_ON_ROOT, > + }, > + > + { > + .name = "cpus.effective", > + .seq_show = cpuset_common_seq_show, > + .private = FILE_EFFECTIVE_CPULIST, > + .flags = CFTYPE_NOT_ON_ROOT, > + }, > + > + { > + .name = "mems.effective", > + .seq_show = cpuset_common_seq_show, > + .private = FILE_EFFECTIVE_MEMLIST, > + .flags = CFTYPE_NOT_ON_ROOT, > + }, > + > + { } /* terminate */ > +}; > + > + > +/* > * cpuset_css_alloc - allocate a cpuset css > * cgrp: control group that the new cpuset will be part of > */ > @@ -2104,8 +2144,10 @@ struct cgroup_subsys cpuset_cgrp_subsys = { > .post_attach = cpuset_post_attach, > .bind = cpuset_bind, > .fork = cpuset_fork, > - .legacy_cftypes = files, > + .legacy_cftypes = legacy_files, > + .dfl_cftypes = dfl_files, > .early_init = true, > + .threaded = true, Which means that by default we can attach tasks instead of only processes, right? > }; > > /** > -- > 1.8.3.1 > -- #include Patrick Bellasi