From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S936135AbcHBRmX (ORCPT ); Tue, 2 Aug 2016 13:42:23 -0400 Received: from mail-db5eur01on0090.outbound.protection.outlook.com ([104.47.2.90]:50539 "EHLO EUR01-DB5-obe.outbound.protection.outlook.com" rhost-flags-OK-OK-OK-FAIL) by vger.kernel.org with ESMTP id S968133AbcHBRhb (ORCPT ); Tue, 2 Aug 2016 13:37:31 -0400 Authentication-Results: spf=none (sender IP is ) smtp.mailfrom=VDavydov@virtuozzo.com; From: Vladimir Davydov To: Andrew Morton CC: , Johannes Weiner , "Michal Hocko" , , Subject: [PATCH v2 1/3] mm: memcontrol: fix swap counter leak on swapout from offline cgroup Date: Tue, 2 Aug 2016 18:00:48 +0300 Message-ID: X-Mailer: git-send-email 2.1.4 MIME-Version: 1.0 Content-Type: text/plain X-Originating-IP: [195.214.232.10] X-ClientProxiedBy: AM2PR09CA0004.eurprd09.prod.outlook.com (10.161.22.142) To AM5PR0801MB1860.eurprd08.prod.outlook.com (10.168.157.17) X-MS-Office365-Filtering-Correlation-Id: 723d7c9f-4b2e-4ae1-c696-08d3bae5cfb1 X-Microsoft-Exchange-Diagnostics: 1;AM5PR0801MB1860;2:hUXanl8nwloKiRRvoocb2RLQiwst91MZBz3TADmZZr/k9kisfIFjqdoFp6iY5tkzyKZYFAbT1Yzc0n9OW6qrEs6DqfsJTJPMgiCFkkoxhDOcr7XmltnD8rfFgNaNjddCEfHLLaj8zNNglvyg/NXtTIh0wUXcAzYmERwg3bO6AVsbnTVP1CFshVhLwH6vEsXy;3:p5WvQd3mNSEUhGW2MYIFqHCrjO3mKJzWMYSvnBHBUVMAECwh+o7O3zfy9GYSjUOdnIO5lV76JkaOSu1aVRRD+Bo062nBwKiehm1Vz4CbHcm5GQs2TddWpGChY+u2Xr5f X-Microsoft-Antispam: UriScan:;BCL:0;PCL:0;RULEID:;SRVR:AM5PR0801MB1860; X-Microsoft-Exchange-Diagnostics: 1;AM5PR0801MB1860;25:V1ydCfC2RBTPUchaTpBH2wcYCaHOuIa/5YBaPmwLFp+hpZWhAClPiI/2M6dl853XxkoSXw9y2+rqUxjFMAdHvIsklJI86U73AFOF7dm1wjeUxXif/GGJOkHXTqtyq40Gnxm5GSowvW8oXpcug9CR2rrCpnHPX4TNurJlfDsBahFon1sm1i50efORB4g5pgMTjGd6MEvIu5w4M770x4o/Y+fxcxsrsecTRq4W2f4otnymGlNWtMz9MfaNqa8drh+bFBaBam99T/Kh55yjLo4lsRbU5Y3jYoIQSTyTYyurH69LiUJtvwyS12Ub6ln+tqKUn9fWs6xU3nA3AoGjFo+9YZxCcWuxCzgDlvLWXz4gNT2974HwRWHL3mqnsuLm3eO8IXuulVD0cO5AtDoel/l5LQjaX0zqvyTWrm7PRAQQXGQaSwV7SmAgn6otczQBLyzZ5XUpQIbw2aJwL0O8ZYzgwFJMEo1ZtgJFNO2DdMN7LZojoG6a9F9XyZKB0mGITmp2uHqWP91lALxGq3wxdg63vVg0OH7ooGyOfRyxsoMi5K/0SiH5D3sAb+NSHNrcovmP91FR5eE+kZaIPXkpfBN+lN/M5KccdrJ7KP05H0ash3xaYKywle0KZ6QgXftdEKYRhbbENBZMEP60j7jhXz38Zp12kFNngJUjObE1TNQUq+kkARhH4HCl7/l3sPYO6lJxVomAVR7Ha+mYqAVGtrDjsQ==;31:OP9tYHCuMgUP/WxyI22AzlOvVo9rCuvukpQKIPy/b/24GOmRZ2uUidLBB167HxOPpSBe0yfXy3n+oMeVSkhGSaNEFVoE+weOrzaAQVFEdAriW3tboG5Odt3+gP2OXopSdRQMtKr0+mtLpKoJXtBVziQm9oUvElsDQjrIo5Pb9lQDvRbtLDQG6P63RpF4koVgeJJBZbLnGjcXEGKng138Q2TE026bSm494t343VP4gkY= X-Microsoft-Antispam-PRVS: X-Exchange-Antispam-Report-Test: UriScan:(9452136761055); X-Exchange-Antispam-Report-CFA-Test: BCL:0;PCL:0;RULEID:(6040130)(601004)(2401047)(8121501046)(5005006)(3002001)(10201501046)(6041072)(6043046);SRVR:AM5PR0801MB1860;BCL:0;PCL:0;RULEID:;SRVR:AM5PR0801MB1860; X-Microsoft-Exchange-Diagnostics: 1;AM5PR0801MB1860;4:6zzMnHxE41tMlam+n9RZgWL0AMSTZ0K+/XF4qKWeNqAACSOsRwyM1dC8W+absNMB36w/zkXJL+B8dB9WQovuXvi8GgXAXEdB858A3k4ocptfbSJ35gGIT1du1qdZSIViNrlXFQ/5PWoDHIbE1DoYRO3VkoSTaQ3wl33VX6Pc77kZFrzmdUfzDP6dvNyBPEzgBaAy+FKUUphVKEtX7FhKshOYVuZZXf68pnUYbvu8Mfg4ucmwRpGx7B6ayF3cOuv36cf35/OrDTBuKGRmqZ+btT0g5I+XoNC0T6v9J1m4cmhVf9mKyrbWmgrViWvFKf2EzUvYGbQGXpWHEJjTpowdy2HFIfILxr43TTHaJw//pJPUfT7Vb9hfnrdMNRfp+u+4QAowucTXoFv6pZrpJdN8lbsAZrl7iphBRDaPrx1GWlLJPF0do7mpaIPJoqeJ5ggxOWDleuXNBHdqgR5pPUdbQA== X-Forefront-PRVS: 0022134A87 X-Forefront-Antispam-Report: SFV:NSPM;SFS:(10019020)(4630300001)(6009001)(7916002)(189002)(199003)(105586002)(101416001)(33646002)(36756003)(47776003)(8676002)(86362001)(42186005)(229853001)(4326007)(106356001)(118296001)(2906002)(21086003)(305945005)(19580395003)(3846002)(92566002)(19580405001)(586003)(5003940100001)(7736002)(50466002)(50226002)(110136002)(77096005)(81156014)(6116002)(69596002)(81166006)(48376002)(80792005)(66066001)(97736004)(7846002)(50986999)(68736007)(189998001);DIR:OUT;SFP:1102;SCL:1;SRVR:AM5PR0801MB1860;H:virtuozzo.com;FPR:;SPF:None;PTR:InfoNoRecords;MX:1;A:1;LANG:en; X-Microsoft-Exchange-Diagnostics: =?us-ascii?Q?1;AM5PR0801MB1860;23:rYP6RTWNmJgO7K2Zfg5pq5bO/I11Cw7kLS6XvEm?= =?us-ascii?Q?iEqtgQcnNzsND3RVMWxS0U+7Ed1kQ/D5Hk/JDhWxewZKmD4YRy4pzf4Icj+5?= =?us-ascii?Q?abAjMPqqLIKBm86tS+gnPQUU5cYMhtTZELh66SQ46PGsGCCl54wxH/Ri3b/J?= =?us-ascii?Q?yAWtRDAADuhYAJaraGNZQNhapwDMdcd2nj6d33twUklAN7RO3vOxi5bRxNGe?= =?us-ascii?Q?3L+oasfrzPunOga2eHDC6RQieegFcnp2OYrtROuJ2YRJhbuS2KZJ0cAMUUPG?= =?us-ascii?Q?sw4fhESdSRZi5Pg4HN9UvMlp5ZYkmME2KR884RwRrs9b5KfokYsTWt6KMdtt?= =?us-ascii?Q?CM0KrrJSeLsMPlXuiAwEAAl2lR3X3yNdWR7lbCR0MVmrVHSCAz9RotjtjxF8?= =?us-ascii?Q?SfNBQvK9w5P/x295GHHnijttoYBlYb1DSvJM8g0sQSjxjQeDFcHsxZrGlzCO?= =?us-ascii?Q?jwQVmd5l83xOYtesZFI04Ckk97yA82UKOAGRWksuoRrY7M8Dd1ipmoBCKkXD?= =?us-ascii?Q?3UJcf8DTUQMgHVfozft1whkIzKYJW6EDAR8iamVp2XC9t11+D/p/AsGT4McF?= =?us-ascii?Q?OBdKl3cF+Pyp5kFobkEmER0w53liAGJ54jKZJ/YBcM1CkZ+sVtSUda/6dwdi?= =?us-ascii?Q?kJydgrIjHZ2pFzzxe0K1GQPU78CkV8ZdLzs0CEVF/DTbPvfee05ygzBKHUzI?= =?us-ascii?Q?hCogKnqf1xEUwr/8JtFaj746JxvSKx2PNQij/5WAyhgjzW3f5Cv6Fqf7jt5Q?= =?us-ascii?Q?129pcru0YDehDsXlEFlKtqEhx4ZJfBnSKGcmad0J4TeJzDB8jd5s3BXDgYPW?= =?us-ascii?Q?x3XVKkwIlui20hmciRChbWvBlo8UUMp3jIOsXWz6OnURqP8819OFVDdLJHSt?= =?us-ascii?Q?KIDjH8/8/lBtAQDjZCornCwo7z/MDqlm1ETxFfZY68zhI8eT7RV+8Fyg14SA?= =?us-ascii?Q?vKItN3c1ZSisIoFrFQJk9/qvHMmlk+/PCuPwxDXBW8xCbBfUhzH73WtW1IOH?= =?us-ascii?Q?Ns8mrV3VQFpTHC+P/LHlCLEXiy/WRKI0IRyPwi9BZSGIkS0mUUlTZ+xSbjn7?= =?us-ascii?Q?XuzTmS6dtdtc0g3TsdMsOrBaMnPb/61noewR24qLK+4SzQJPmhA=3D=3D?= X-Microsoft-Exchange-Diagnostics: 1;AM5PR0801MB1860;6:TNSzWTLkqcLcduQrimPSvAYcWUk/CINJx/4DjWVKSHEyKer3NReHE4L0IHWSO6Huuy0pu1izqxFZn2DIqxjsUt9L0+aJb3+7R5Neo1ysl+d9DiT9Zyo/vAoslPE8sUGXM7hWQwnq+kMXrEedojiJDAfRnW2DNY44BJWm5LvEyQvK3ErkCs+eMldr3ejeGrgOP7WBmIpWzVe/k1cH3uwof4PoIo7XTeYe5RzTeYnU/902TOM4lgDiqZUKpOsUgs1wA4Vab6fGd7e58p3p3qQfXt9qVg7rUBdZ6hLZdxKFiqyKkmNgkC5uVTtTtwDG57YJ;5:uS7qM5B1IWUDdFfG5mMgAllVXB4y8l9YCtpV2bhLJxDzRoQN8f0uIslUh1Gdkcrl/mJzk6cLe2z6hhpQ8fc5z6m7J+h29qWlAMjd2ckO4a3QLRKm0nwYhi8PdfwnTtV94jzqdnhOILdKrnSo85UY2A==;24:O85U23K8xfag3Jpex8i3m5GWlVwzWhSAA4liLVjsaETvMT4zwu1wa1aVlydwcIMg50bGFz3rFUDeSoplYGqrc/x6XhjJoGxXaLxqkSZEXQU=;7:niVKcLM/xEv3zcZETVAbZjtr8K5e8hTlO6HbSzkG1EhKToosNzR7oVYm0SSYQsf5moS6bN3OQ8WXK9cwnhfOgqREUb/iKdIQCS8KNRg+l4VZqzY0QP06dinhuvtHMEkXnnZBwjRouX5UFP1C76bD1sjGl+638mXI4LDud0t2F4859wYeny1CFYwthm5S3Aso6DhMW7q7TNEXSi/q6gcsNHoOKhcRfq1jd7EgyLIE3oR9oA8bB9CcmEIDz5ZEnJEZ SpamDiagnosticOutput: 1:99 SpamDiagnosticMetadata: NSPM X-Microsoft-Exchange-Diagnostics: 1;AM5PR0801MB1860;20:SnZ7YTe7Ercs4Q/l8cuxFEMdy/97SQydpdzgnoa3pVmk92/CSknafb4cwXMhuDojRKmikvj3OScbetIpAIwwz2aPNHrvd3K3x/PoUlj/kw1l5K02ADnuyJoKhbWRH6+zrw+5la7wLGwkrPI/o7HTcgqBJ9ApvruYV5GGK/W95UI= X-OriginatorOrg: virtuozzo.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 02 Aug 2016 15:00:58.0370 (UTC) X-MS-Exchange-CrossTenant-FromEntityHeader: Hosted X-MS-Exchange-Transport-CrossTenantHeadersStamped: AM5PR0801MB1860 Sender: linux-kernel-owner@vger.kernel.org List-ID: X-Mailing-List: linux-kernel@vger.kernel.org An offline memory cgroup might have anonymous memory or shmem left charged to it and no swap. Since only swap entries pin the id of an offline cgroup, such a cgroup will have no id and so an attempt to swapout its anon/shmem will not store memory cgroup info in the swap cgroup map. As a result, memcg->swap or memcg->memsw will never get uncharged from it and any of its ascendants. Fix this by always charging swapout to the first ancestor cgroup that hasn't released its id yet. Fixes: 73f576c04b941 ("mm: memcontrol: fix cgroup creation failure after many small jobs") Signed-off-by: Vladimir Davydov Cc: [3.19+] --- Changes in v2: - handle !use_hierarchy case properly (Michal) mm/memcontrol.c | 38 ++++++++++++++++++++++++++++++++------ 1 file changed, 32 insertions(+), 6 deletions(-) diff --git a/mm/memcontrol.c b/mm/memcontrol.c index 3be791afd372..4ae12effe347 100644 --- a/mm/memcontrol.c +++ b/mm/memcontrol.c @@ -4036,6 +4036,24 @@ static void mem_cgroup_id_get(struct mem_cgroup *memcg) atomic_inc(&memcg->id.ref); } +static struct mem_cgroup *mem_cgroup_id_get_active(struct mem_cgroup *memcg) +{ + while (!atomic_inc_not_zero(&memcg->id.ref)) { + /* + * The root cgroup cannot be destroyed, so it's refcount must + * always be >= 1. + */ + if (memcg == root_mem_cgroup) { + VM_BUG_ON(1); + break; + } + memcg = parent_mem_cgroup(memcg); + if (!memcg) + memcg = root_mem_cgroup; + } + return memcg; +} + static void mem_cgroup_id_put(struct mem_cgroup *memcg) { if (atomic_dec_and_test(&memcg->id.ref)) { @@ -5752,7 +5770,7 @@ subsys_initcall(mem_cgroup_init); */ void mem_cgroup_swapout(struct page *page, swp_entry_t entry) { - struct mem_cgroup *memcg; + struct mem_cgroup *memcg, *swap_memcg; unsigned short oldid; VM_BUG_ON_PAGE(PageLRU(page), page); @@ -5767,15 +5785,20 @@ void mem_cgroup_swapout(struct page *page, swp_entry_t entry) if (!memcg) return; - mem_cgroup_id_get(memcg); - oldid = swap_cgroup_record(entry, mem_cgroup_id(memcg)); + swap_memcg = mem_cgroup_id_get_active(memcg); + oldid = swap_cgroup_record(entry, mem_cgroup_id(swap_memcg)); VM_BUG_ON_PAGE(oldid, page); - mem_cgroup_swap_statistics(memcg, true); + mem_cgroup_swap_statistics(swap_memcg, true); page->mem_cgroup = NULL; if (!mem_cgroup_is_root(memcg)) page_counter_uncharge(&memcg->memory, 1); + if (memcg != swap_memcg) { + if (!mem_cgroup_is_root(swap_memcg)) + page_counter_charge(&swap_memcg->memsw, 1); + page_counter_uncharge(&memcg->memsw, 1); + } /* * Interrupts should be disabled here because the caller holds the @@ -5815,11 +5838,14 @@ int mem_cgroup_try_charge_swap(struct page *page, swp_entry_t entry) if (!memcg) return 0; + memcg = mem_cgroup_id_get_active(memcg); + if (!mem_cgroup_is_root(memcg) && - !page_counter_try_charge(&memcg->swap, 1, &counter)) + !page_counter_try_charge(&memcg->swap, 1, &counter)) { + mem_cgroup_id_put(memcg); return -ENOMEM; + } - mem_cgroup_id_get(memcg); oldid = swap_cgroup_record(entry, mem_cgroup_id(memcg)); VM_BUG_ON_PAGE(oldid, page); mem_cgroup_swap_statistics(memcg, true); -- 2.1.4