[RHEL7,COMMIT] ms/quota: Do not dirty bad dquots

Submitted by Konstantin Khorenko on Jan. 30, 2020, 7:26 p.m.

Details

Message ID 202001301926.00UJQn98015121@finist-ce7.sw.ru
State New
Series "Series without cover letter"
Headers show

Commit Message

Konstantin Khorenko Jan. 30, 2020, 7:26 p.m.
The commit is pushed to "branch-rh7-3.10.0-1062.7.1.vz7.130.x-ovz" and will appear at https://src.openvz.org/scm/ovz/vzkernel.git
after rh7-3.10.0-1062.7.1.vz7.130.13
------>
commit 5654cfe482c37c733c6c8804675acc84eb34b15a
Author: Jan Kara <jack@suse.cz>
Date:   Thu Jan 30 22:26:49 2020 +0300

    ms/quota: Do not dirty bad dquots
    
    Currently we mark dirty even dquots that are not active (i.e.,
    initialization or reading failed for them). Thus later we have to check
    whether dirty dquot is really active and just clear the dirty bit if
    not. Avoid this complication by just never marking non-active dquot as
    dirty.
    
    Signed-off-by: Jan Kara <jack@suse.cz>
    
    https://jira.sw.ru/browse/PSBM-101043
    (cherry picked from commit 4580b30ea887fc27e57dabd56724ca24d936dc8a)
    Signed-off-by: Andrey Ryabinin <aryabinin@virtuozzo.com>
---
 fs/quota/dquot.c | 15 +++++++--------
 1 file changed, 7 insertions(+), 8 deletions(-)

Patch hide | download patch | download mbox

diff --git a/fs/quota/dquot.c b/fs/quota/dquot.c
index ec672add10897..bc5ff11f68b8c 100644
--- a/fs/quota/dquot.c
+++ b/fs/quota/dquot.c
@@ -342,6 +342,9 @@  int dquot_mark_dquot_dirty(struct dquot *dquot)
 {
 	int ret = 1;
 
+	if (!test_bit(DQ_ACTIVE_B, &dquot->dq_flags))
+		return 0;
+
 	/* If quota is dirty already, we don't have to acquire dq_list_lock */
 	if (test_bit(DQ_MOD_B, &dquot->dq_flags))
 		return 1;
@@ -621,11 +624,9 @@  int dquot_writeback_dquots(struct super_block *sb, int type)
 		while (!list_empty(dirty)) {
 			dquot = list_first_entry(dirty, struct dquot,
 						 dq_dirty);
-			/* Dirty and inactive can be only bad dquot... */
-			if (!test_bit(DQ_ACTIVE_B, &dquot->dq_flags)) {
-				clear_dquot_dirty(dquot);
-				continue;
-			}
+
+			WARN_ON(!test_bit(DQ_ACTIVE_B, &dquot->dq_flags));
+
 			/* Now we have active dquot from which someone is
  			 * holding reference so we can safely just increase
 			 * use count */
@@ -759,7 +760,7 @@  void dqput(struct dquot *dquot)
 		return;
 	}
 	/* Need to release dquot? */
-	if (test_bit(DQ_ACTIVE_B, &dquot->dq_flags) && dquot_dirty(dquot)) {
+	if (dquot_dirty(dquot)) {
 		spin_unlock(&dq_list_lock);
 		/* Commit dquot before releasing */
 		ret = dquot->dq_sb->dq_op->write_dquot(dquot);
@@ -777,8 +778,6 @@  void dqput(struct dquot *dquot)
 		}
 		goto we_slept;
 	}
-	/* Clear flag in case dquot was inactive (something bad happened) */
-	clear_dquot_dirty(dquot);
 	if (test_bit(DQ_ACTIVE_B, &dquot->dq_flags)) {
 		spin_unlock(&dq_list_lock);
 		dquot->dq_sb->dq_op->release_dquot(dquot);