From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-16.6 required=3.0 tests=BAYES_00,DKIM_INVALID, DKIM_SIGNED,HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_CR_TRAILER,INCLUDES_PATCH, MAILING_LIST_MULTI,SPF_HELO_NONE,SPF_PASS,USER_AGENT_GIT autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 19718C07E95 for ; Tue, 13 Jul 2021 10:36:39 +0000 (UTC) Received: from kanga.kvack.org (kanga.kvack.org [205.233.56.17]) by mail.kernel.org (Postfix) with ESMTP id B5AAA6120A for ; Tue, 13 Jul 2021 10:36:38 +0000 (UTC) DMARC-Filter: OpenDMARC Filter v1.3.2 mail.kernel.org B5AAA6120A Authentication-Results: mail.kernel.org; dmarc=none (p=none dis=none) header.from=suse.cz Authentication-Results: mail.kernel.org; spf=pass smtp.mailfrom=owner-linux-mm@kvack.org Received: by kanga.kvack.org (Postfix) id A8A466B0098; Tue, 13 Jul 2021 06:36:33 -0400 (EDT) Received: by kanga.kvack.org (Postfix, from userid 40) id 7C67E8D0001; Tue, 13 Jul 2021 06:36:33 -0400 (EDT) X-Delivered-To: int-list-linux-mm@kvack.org Received: by kanga.kvack.org (Postfix, from userid 63042) id 5067B6B009C; Tue, 13 Jul 2021 06:36:33 -0400 (EDT) X-Delivered-To: linux-mm@kvack.org Received: from forelay.hostedemail.com (smtprelay0070.hostedemail.com [216.40.44.70]) by kanga.kvack.org (Postfix) with ESMTP id 0C8C96B0098 for ; Tue, 13 Jul 2021 06:36:33 -0400 (EDT) Received: from smtpin17.hostedemail.com (10.5.19.251.rfc1918.com [10.5.19.251]) by forelay05.hostedemail.com (Postfix) with ESMTP id 143F3183BFAB7 for ; Tue, 13 Jul 2021 10:36:32 +0000 (UTC) X-FDA: 78357210624.17.830F31D Received: from smtp-out1.suse.de (smtp-out1.suse.de [195.135.220.28]) by imf16.hostedemail.com (Postfix) with ESMTP id 86C59F000095 for ; Tue, 13 Jul 2021 10:36:31 +0000 (UTC) Received: from relay2.suse.de (relay2.suse.de [149.44.160.134]) by smtp-out1.suse.de (Postfix) with ESMTP id 747AD22290; Tue, 13 Jul 2021 10:36:30 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=suse.cz; s=susede2_rsa; t=1626172590; h=from:from:reply-to:date:date:message-id:message-id:to:to:cc:cc: mime-version:mime-version: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=Hx7/uzoxBpb7N/mq/37Hb9gHMhm+pF/hrO5pKRztXdE=; b=O1p0EGOIF+3s6kYedUZfMYaAngfG9sMxvMPxlU4zcsqp8k7iu/uYVqzQ5ROuGnQVmlQSKB z2VffMPdtAv7Ad43iuo3I5CmtzP0hGdTQELZ3MIEu1KpZPmWHYtnzEXYbal6NUFIlFKOF8 nzK2gDHu03OaVe3wDVkuyxqivzupVYs= DKIM-Signature: v=1; a=ed25519-sha256; c=relaxed/relaxed; d=suse.cz; s=susede2_ed25519; t=1626172590; h=from:from:reply-to:date:date:message-id:message-id:to:to:cc:cc: mime-version:mime-version: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=Hx7/uzoxBpb7N/mq/37Hb9gHMhm+pF/hrO5pKRztXdE=; b=hIqtooHbksss0aGgndN5y8fppu1oaorIEaIWA3N+EWmTHpSKRi2gQNBXY1SWJeDLqf/mXY nHY9ESn80geuAvDg== Received: from quack2.suse.cz (unknown [10.100.224.230]) by relay2.suse.de (Postfix) with ESMTP id 62332A3B81; Tue, 13 Jul 2021 10:36:30 +0000 (UTC) Received: by quack2.suse.cz (Postfix, from userid 1000) id 48D7B1E0BC1; Tue, 13 Jul 2021 12:36:30 +0200 (CEST) From: Jan Kara To: Andrew Morton Cc: , Michael Stapelberg , Wu Fengguang , Jan Kara Subject: [PATCH 2/5] writeback: Reliably update bandwidth estimation Date: Tue, 13 Jul 2021 12:36:26 +0200 Message-Id: <20210713103630.19490-2-jack@suse.cz> X-Mailer: git-send-email 2.26.2 In-Reply-To: <20210713103347.8364-1-jack@suse.cz> References: <20210713103347.8364-1-jack@suse.cz> MIME-Version: 1.0 X-Developer-Signature: v=1; a=openpgp-sha256; l=6441; h=from:subject; bh=9FbHq/XHBMo8KM5eSan6SKR2xZJ+tB7OoKToTBraeEQ=; b=owEBbQGS/pANAwAIAZydqgc/ZEDZAcsmYgBg7WyprDBzGdNmOUNkHywvkE+5z3lw6ib1mX/pL9k7 whguzUeJATMEAAEIAB0WIQSrWdEr1p4yirVVKBycnaoHP2RA2QUCYO1sqQAKCRCcnaoHP2RA2TIzCA CNcSuxStY/o67FfDZ3+FwwkQJhbDaicwUo3gXnJ43eoVqTRTmJnNj+F+QaVQcS69Ic+p1nm3kSwXEd hLUk/3/F3cU3Mi8BbAs+GwBrd15WZ8dHMtXl3Afm0r75/tdnX+aoFcQZIluS9VZLzBWVOa4tSg2DUq A0B5rU9PT9UcQAToAMHSHqHnr6r/Yp/5CSou6bJjBZxjC3/mEXVCLkw6jeiXENmSoXOt9OSUSib6UL VOxNPbRAbaadXt+qYgZk9cUtedXKsWjE9iownoFeBXttTk6iqx7QCoaJJk2hzlRAzi3YXuvKgKbSCh OqIu6IOBvoZGPCLk2482uZgpddEJvu X-Developer-Key: i=jack@suse.cz; a=openpgp; fpr=93C6099A142276A28BBE35D815BC833443038D8C Authentication-Results: imf16.hostedemail.com; dkim=pass header.d=suse.cz header.s=susede2_rsa header.b=O1p0EGOI; dkim=pass header.d=suse.cz header.s=susede2_ed25519 header.b=hIqtooHb; spf=pass (imf16.hostedemail.com: domain of jack@suse.cz designates 195.135.220.28 as permitted sender) smtp.mailfrom=jack@suse.cz; dmarc=none X-Rspamd-Server: rspam02 X-Stat-Signature: 5hgxjf5en3cepczopghbsawo1sjkgps8 X-Rspamd-Queue-Id: 86C59F000095 X-HE-Tag: 1626172591-891846 Content-Transfer-Encoding: quoted-printable X-Bogosity: Ham, tests=bogofilter, spamicity=0.000000, version=1.2.4 Sender: owner-linux-mm@kvack.org Precedence: bulk X-Loop: owner-majordomo@kvack.org List-ID: Currently we trigger writeback bandwidth estimation from balance_dirty_pages() and from wb_writeback(). However neither of these need to trigger when the system is relatively idle and writeback is triggered e.g. from fsync(2). Make sure writeback estimates happen reliably by triggering them from do_writepages(). Signed-off-by: Jan Kara --- fs/fs-writeback.c | 3 --- include/linux/backing-dev.h | 19 ++++++++++++++++++ include/linux/writeback.h | 1 - mm/page-writeback.c | 39 +++++++++++++++++++++++++------------ 4 files changed, 46 insertions(+), 16 deletions(-) diff --git a/fs/fs-writeback.c b/fs/fs-writeback.c index 54300f4d38af..9b5fe2968479 100644 --- a/fs/fs-writeback.c +++ b/fs/fs-writeback.c @@ -2001,7 +2001,6 @@ static long writeback_inodes_wb(struct bdi_writebac= k *wb, long nr_pages, static long wb_writeback(struct bdi_writeback *wb, struct wb_writeback_work *work) { - unsigned long wb_start =3D jiffies; long nr_pages =3D work->nr_pages; unsigned long dirtied_before =3D jiffies; struct inode *inode; @@ -2055,8 +2054,6 @@ static long wb_writeback(struct bdi_writeback *wb, progress =3D __writeback_inodes_wb(wb, work); trace_writeback_written(wb, work); =20 - wb_update_bandwidth(wb, wb_start); - /* * Did we write something? Try for more * diff --git a/include/linux/backing-dev.h b/include/linux/backing-dev.h index 44df4fcef65c..a5d7d625dcc6 100644 --- a/include/linux/backing-dev.h +++ b/include/linux/backing-dev.h @@ -288,6 +288,17 @@ static inline struct bdi_writeback *inode_to_wb(cons= t struct inode *inode) return inode->i_wb; } =20 +static inline struct bdi_writeback *inode_to_wb_wbc( + struct inode *inode, + struct writeback_control *wbc) +{ + /* + * If wbc does not have inode attached, it means cgroup writeback was + * disabled when wbc started. Just use the default wb in that case. + */ + return wbc->wb ? wbc->wb : &inode_to_bdi(inode)->wb; +} + /** * unlocked_inode_to_wb_begin - begin unlocked inode wb access transacti= on * @inode: target inode @@ -366,6 +377,14 @@ static inline struct bdi_writeback *inode_to_wb(stru= ct inode *inode) return &inode_to_bdi(inode)->wb; } =20 +static inline struct bdi_writeback *inode_to_wb_wbc( + struct inode *inode, + struct writeback_control *wbc) +{ + return inode_to_wb(inode); +} + + static inline struct bdi_writeback * unlocked_inode_to_wb_begin(struct inode *inode, struct wb_lock_cookie *c= ookie) { diff --git a/include/linux/writeback.h b/include/linux/writeback.h index 667e86cfbdcf..2480322c06a7 100644 --- a/include/linux/writeback.h +++ b/include/linux/writeback.h @@ -379,7 +379,6 @@ int dirty_writeback_centisecs_handler(struct ctl_tabl= e *table, int write, void global_dirty_limits(unsigned long *pbackground, unsigned long *pdir= ty); unsigned long wb_calc_thresh(struct bdi_writeback *wb, unsigned long thr= esh); =20 -void wb_update_bandwidth(struct bdi_writeback *wb, unsigned long start_t= ime); void balance_dirty_pages_ratelimited(struct address_space *mapping); bool wb_over_bg_thresh(struct bdi_writeback *wb); =20 diff --git a/mm/page-writeback.c b/mm/page-writeback.c index e1aa1c9d8e36..e4a381b8944b 100644 --- a/mm/page-writeback.c +++ b/mm/page-writeback.c @@ -1332,7 +1332,6 @@ static void wb_update_dirty_ratelimit(struct dirty_= throttle_control *dtc, =20 static void __wb_update_bandwidth(struct dirty_throttle_control *gdtc, struct dirty_throttle_control *mdtc, - unsigned long start_time, bool update_ratelimit) { struct bdi_writeback *wb =3D gdtc->wb; @@ -1352,13 +1351,6 @@ static void __wb_update_bandwidth(struct dirty_thr= ottle_control *gdtc, dirtied =3D percpu_counter_read(&wb->stat[WB_DIRTIED]); written =3D percpu_counter_read(&wb->stat[WB_WRITTEN]); =20 - /* - * Skip quiet periods when disk bandwidth is under-utilized. - * (at least 1s idle time between two flusher runs) - */ - if (elapsed > HZ && time_before(wb->bw_time_stamp, start_time)) - goto snapshot; - if (update_ratelimit) { domain_update_bandwidth(gdtc, now); wb_update_dirty_ratelimit(gdtc, dirtied, elapsed); @@ -1374,17 +1366,36 @@ static void __wb_update_bandwidth(struct dirty_th= rottle_control *gdtc, } wb_update_write_bandwidth(wb, elapsed, written); =20 -snapshot: wb->dirtied_stamp =3D dirtied; wb->written_stamp =3D written; wb->bw_time_stamp =3D now; } =20 -void wb_update_bandwidth(struct bdi_writeback *wb, unsigned long start_t= ime) +static void wb_update_bandwidth(struct bdi_writeback *wb) { struct dirty_throttle_control gdtc =3D { GDTC_INIT(wb) }; =20 - __wb_update_bandwidth(&gdtc, NULL, start_time, false); + spin_lock(&wb->list_lock); + __wb_update_bandwidth(&gdtc, NULL, false); + spin_unlock(&wb->list_lock); +} + +/* Interval after which we consider wb idle and don't estimate bandwidth= */ +#define WB_BANDWIDTH_IDLE_JIF (HZ) + +static void wb_bandwidth_estimate_start(struct bdi_writeback *wb) +{ + unsigned long now =3D jiffies; + unsigned long elapsed =3D now - READ_ONCE(wb->bw_time_stamp); + + if (elapsed > WB_BANDWIDTH_IDLE_JIF && + !atomic_read(&wb->writeback_inodes)) { + spin_lock(&wb->list_lock); + wb->dirtied_stamp =3D wb_stat(wb, WB_DIRTIED); + wb->written_stamp =3D wb_stat(wb, WB_WRITTEN); + wb->bw_time_stamp =3D now; + spin_unlock(&wb->list_lock); + } } =20 /* @@ -1713,7 +1724,7 @@ static void balance_dirty_pages(struct bdi_writebac= k *wb, if (time_is_before_jiffies(wb->bw_time_stamp + BANDWIDTH_INTERVAL)) { spin_lock(&wb->list_lock); - __wb_update_bandwidth(gdtc, mdtc, start_time, true); + __wb_update_bandwidth(gdtc, mdtc, true); spin_unlock(&wb->list_lock); } =20 @@ -2347,9 +2358,12 @@ EXPORT_SYMBOL(generic_writepages); int do_writepages(struct address_space *mapping, struct writeback_contro= l *wbc) { int ret; + struct bdi_writeback *wb; =20 if (wbc->nr_to_write <=3D 0) return 0; + wb =3D inode_to_wb_wbc(mapping->host, wbc); + wb_bandwidth_estimate_start(wb); while (1) { if (mapping->a_ops->writepages) ret =3D mapping->a_ops->writepages(mapping, wbc); @@ -2360,6 +2374,7 @@ int do_writepages(struct address_space *mapping, st= ruct writeback_control *wbc) cond_resched(); congestion_wait(BLK_RW_ASYNC, HZ/50); } + wb_update_bandwidth(wb); return ret; } =20 --=20 2.26.2