Received: by 10.223.176.5 with SMTP id f5csp341060wra; Sat, 3 Feb 2018 00:25:49 -0800 (PST) X-Google-Smtp-Source: AH8x224ydHLMNRuNJmdf7UBqIoT2IPtvj5k0jmbg6QHHJl3GWp+NB3iTd80Ay5qtEASYIall6esy X-Received: by 10.98.18.10 with SMTP id a10mr43045329pfj.140.1517646348963; Sat, 03 Feb 2018 00:25:48 -0800 (PST) ARC-Seal: i=1; a=rsa-sha256; t=1517646348; cv=none; d=google.com; s=arc-20160816; b=nzufLhOL7iQsCs0PyFeyDxoKODUZcYAot3X65vaSXUP5Swd1rm48u2214aK2JD9l9u LGrtskeGB+vao39cMnlvjdEEiZKsk5EcngbcKQWMIlGyuE7x4wgPQfcFwS0AVFLTb5BJ lIly+nOIuJ8OHBSRWyzr3aLksddl0IyHesWcl+VFah/ZA7dpR4kEA86hTWKKVtBUgzJl +tmPIfR/xaHMfgQ2B/25e74qMQKmhWCXSy5lA+Bw9iIv2t+ZhAsNKUZL7d2kIM4DNrzf ULf4GgcL/oz1DhhURqXusT1aYPKc4QyET5PciTEQiv44yvfkJnlQV3WCQR5lDtjmUsUU umXw== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:sender:message-id:date:subject:cc:to:from :dkim-signature:arc-authentication-results; bh=0fj33TOfzMUtHqh1NUGvS8TM6vjD1hxQNboc8hD7BXM=; b=EF8t2UMXoKi869/PaPMhGx9AUU8o/+wDCEZyWUpmKkBqGWsgmLK0/AptUL3WC57pdZ q3cjXDBnj6Hb4LfXkjZWupLt45YQURgk5ulp7AdnW6yf+GwtYDM6OkzcWbnvhaVT3HKH 6r4SJBDCVfDXixpgxnx2TQSKnTS0kx0LHJNMVzPZb+MzhiD1x2IXCxBY2AzHHaRW350x k+XqIYHLSrj5/92JmWMv/U/ubeIQAoE4YmIA3l5afPABU3kiuR4hUKMwi+amsieHEsEz F9Ov0XQhfZTmG9Or/30zJ8A5Wzar97G2G3Du7twCxfg3KM+K25DgDsnoz5TrUKKUSyg9 EQCg== ARC-Authentication-Results: i=1; mx.google.com; dkim=fail header.i=@cmpxchg.org header.s=x header.b=mMdfdtri; 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; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=cmpxchg.org Return-Path: Received: from vger.kernel.org (vger.kernel.org. [209.132.180.67]) by mx.google.com with ESMTP id d25-v6si3357347plj.438.2018.02.03.00.25.34; Sat, 03 Feb 2018 00:25:48 -0800 (PST) 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; dkim=fail header.i=@cmpxchg.org header.s=x header.b=mMdfdtri; 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; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=cmpxchg.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1751644AbeBCIXc (ORCPT + 99 others); Sat, 3 Feb 2018 03:23:32 -0500 Received: from gum.cmpxchg.org ([85.214.110.215]:45498 "EHLO gum.cmpxchg.org" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1750725AbeBCIXZ (ORCPT ); Sat, 3 Feb 2018 03:23:25 -0500 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=cmpxchg.org ; s=x; h=Message-Id:Date:Subject:Cc:To:From:Sender:Reply-To:MIME-Version: Content-Type:Content-Transfer-Encoding:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: In-Reply-To:References:List-Id:List-Help:List-Unsubscribe:List-Subscribe: List-Post:List-Owner:List-Archive; bh=0fj33TOfzMUtHqh1NUGvS8TM6vjD1hxQNboc8hD7BXM=; b=mMdfdtrixTzpZzsXgm2rkbTLY5 FVjauMyjX2NCkP89KfaLhcClx29P98cmif0DpjU4crtTdYHDqxtEhPYSMcl/EOGqvQaAHn2lngtcA OUYFPE/3VNEKHjrcCY6zgrN4tlj0EsiYWkRdUtfWGy9wKMVBlZJ+DF8gswZ8RBR4OBJc=; From: Johannes Weiner To: Andrew Morton Cc: Tejun Heo , Michal Hocko , linux-mm@kvack.org, cgroups@vger.kernel.org, linux-kernel@vger.kernel.org, kernel-team@fb.com Subject: [PATCH] mm: memcontrol: fix NR_WRITEBACK leak in memcg and system stats Date: Sat, 3 Feb 2018 03:23:53 -0500 Message-Id: <20180203082353.17284-1-hannes@cmpxchg.org> X-Mailer: git-send-email 2.16.1 Sender: linux-kernel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org After the ("a983b5ebee57 mm: memcontrol: fix excessive complexity in memory.stat reporting"), we observed slowly upward creeping NR_WRITEBACK counts over the course of several days, both the per-memcg stats as well as the system counter in e.g. /proc/meminfo. The conversion from full per-cpu stat counts to per-cpu cached atomic stat counts introduced an irq-unsafe RMW operation into the updates. Most stat updates come from process context, but one notable exception is the NR_WRITEBACK counter. While writebacks are issued from process context, they are retired from (soft)irq context. When writeback completions interrupt the RMW counter updates of new writebacks being issued, the decs from the completions are lost. Since the global updates are routed through the joint lruvec API, both the memcg counters as well as the system counters are affected. This patch makes the joint stat and event API irq safe. Fixes: a983b5ebee57 ("mm: memcontrol: fix excessive complexity in memory.stat reporting") Debugged-by: Tejun Heo Signed-off-by: Johannes Weiner --- include/linux/memcontrol.h | 24 ++++++++++++++++-------- 1 file changed, 16 insertions(+), 8 deletions(-) diff --git a/include/linux/memcontrol.h b/include/linux/memcontrol.h index 882046863581..c46016bb25eb 100644 --- a/include/linux/memcontrol.h +++ b/include/linux/memcontrol.h @@ -523,9 +523,11 @@ static inline void __mod_memcg_state(struct mem_cgroup *memcg, static inline void mod_memcg_state(struct mem_cgroup *memcg, int idx, int val) { - preempt_disable(); + unsigned long flags; + + local_irq_save(flags); __mod_memcg_state(memcg, idx, val); - preempt_enable(); + local_irq_restore(flags); } /** @@ -606,9 +608,11 @@ static inline void __mod_lruvec_state(struct lruvec *lruvec, static inline void mod_lruvec_state(struct lruvec *lruvec, enum node_stat_item idx, int val) { - preempt_disable(); + unsigned long flags; + + local_irq_save(flags); __mod_lruvec_state(lruvec, idx, val); - preempt_enable(); + local_irq_restore(flags); } static inline void __mod_lruvec_page_state(struct page *page, @@ -630,9 +634,11 @@ static inline void __mod_lruvec_page_state(struct page *page, static inline void mod_lruvec_page_state(struct page *page, enum node_stat_item idx, int val) { - preempt_disable(); + unsigned long flags; + + local_irq_save(flags); __mod_lruvec_page_state(page, idx, val); - preempt_enable(); + local_irq_restore(flags); } unsigned long mem_cgroup_soft_limit_reclaim(pg_data_t *pgdat, int order, @@ -659,9 +665,11 @@ static inline void __count_memcg_events(struct mem_cgroup *memcg, static inline void count_memcg_events(struct mem_cgroup *memcg, int idx, unsigned long count) { - preempt_disable(); + unsigned long flags; + + local_irq_save(flags); __count_memcg_events(memcg, idx, count); - preempt_enable(); + local_irq_restore(flags); } /* idx can be of type enum memcg_event_item or vm_event_item */ -- 2.16.1