Blame SOURCES/0049-exfat-write-multiple-sectors-at-once.patch

Kmods SIG 9e3ffb
From 3db3c3fb840ed4a6c7666d1464959edd40fe54f1 Mon Sep 17 00:00:00 2001
Kmods SIG 9e3ffb
From: Tetsuhiro Kohada <kohada.t2@gmail.com>
Kmods SIG 9e3ffb
Date: Tue, 23 Jun 2020 15:22:19 +0900
Kmods SIG 9e3ffb
Subject: [Backport 3db3c3fb840e] exfat: write multiple sectors at once
Kmods SIG 9e3ffb
Kmods SIG 9e3ffb
Write multiple sectors at once when updating dir-entries.
Kmods SIG 9e3ffb
Add exfat_update_bhs() for that. It wait for write completion once
Kmods SIG 9e3ffb
instead of sector by sector.
Kmods SIG 9e3ffb
It's only effective if sync enabled.
Kmods SIG 9e3ffb
Kmods SIG 9e3ffb
Signed-off-by: Tetsuhiro Kohada <kohada.t2@gmail.com>
Kmods SIG 9e3ffb
Signed-off-by: Namjae Jeon <namjae.jeon@samsung.com>
Kmods SIG 9e3ffb
---
Kmods SIG 9e3ffb
 src/dir.c      | 15 +++++++++------
Kmods SIG 9e3ffb
 src/exfat_fs.h |  1 +
Kmods SIG 9e3ffb
 src/misc.c     | 19 +++++++++++++++++++
Kmods SIG 9e3ffb
 3 files changed, 29 insertions(+), 6 deletions(-)
Kmods SIG 9e3ffb
Kmods SIG 9e3ffb
diff --git a/src/dir.c b/src/dir.c
Kmods SIG 9e3ffb
index 97296bc2b241cbe40b9a87e1f11ef8c203881680..542f1a5ab56fd60a2498f4437c85875cb07e9ef2 100644
Kmods SIG 9e3ffb
--- a/src/dir.c
Kmods SIG 9e3ffb
+++ b/src/dir.c
Kmods SIG 9e3ffb
@@ -606,13 +606,16 @@ void exfat_update_dir_chksum_with_entry_set(struct exfat_entry_set_cache *es)
Kmods SIG 9e3ffb
 
Kmods SIG 9e3ffb
 void exfat_free_dentry_set(struct exfat_entry_set_cache *es, int sync)
Kmods SIG 9e3ffb
 {
Kmods SIG 9e3ffb
-	int i;
Kmods SIG 9e3ffb
+	int i, err = 0;
Kmods SIG 9e3ffb
 
Kmods SIG 9e3ffb
-	for (i = 0; i < es->num_bh; i++) {
Kmods SIG 9e3ffb
-		if (es->modified)
Kmods SIG 9e3ffb
-			exfat_update_bh(es->bh[i], sync);
Kmods SIG 9e3ffb
-		brelse(es->bh[i]);
Kmods SIG 9e3ffb
-	}
Kmods SIG 9e3ffb
+	if (es->modified)
Kmods SIG 9e3ffb
+		err = exfat_update_bhs(es->bh, es->num_bh, sync);
Kmods SIG 9e3ffb
+
Kmods SIG 9e3ffb
+	for (i = 0; i < es->num_bh; i++)
Kmods SIG 9e3ffb
+		if (err)
Kmods SIG 9e3ffb
+			bforget(es->bh[i]);
Kmods SIG 9e3ffb
+		else
Kmods SIG 9e3ffb
+			brelse(es->bh[i]);
Kmods SIG 9e3ffb
 	kfree(es);
Kmods SIG 9e3ffb
 }
Kmods SIG 9e3ffb
 
Kmods SIG 9e3ffb
diff --git a/src/exfat_fs.h b/src/exfat_fs.h
Kmods SIG 9e3ffb
index 05553b2924ee313d9341bc8585f2290a10e8ff56..af0f526eece7bd05caa6a1b7fae28701776df5ed 100644
Kmods SIG 9e3ffb
--- a/src/exfat_fs.h
Kmods SIG 9e3ffb
+++ b/src/exfat_fs.h
Kmods SIG 9e3ffb
@@ -513,6 +513,7 @@ void exfat_set_entry_time(struct exfat_sb_info *sbi, struct timespec64 *ts,
Kmods SIG 9e3ffb
 u16 exfat_calc_chksum16(void *data, int len, u16 chksum, int type);
Kmods SIG 9e3ffb
 u32 exfat_calc_chksum32(void *data, int len, u32 chksum, int type);
Kmods SIG 9e3ffb
 void exfat_update_bh(struct buffer_head *bh, int sync);
Kmods SIG 9e3ffb
+int exfat_update_bhs(struct buffer_head **bhs, int nr_bhs, int sync);
Kmods SIG 9e3ffb
 void exfat_chain_set(struct exfat_chain *ec, unsigned int dir,
Kmods SIG 9e3ffb
 		unsigned int size, unsigned char flags);
Kmods SIG 9e3ffb
 void exfat_chain_dup(struct exfat_chain *dup, struct exfat_chain *ec);
Kmods SIG 9e3ffb
diff --git a/src/misc.c b/src/misc.c
Kmods SIG 9e3ffb
index 8a3dde59052bf04a4de6f65554df14ed6f185147..d34e6193258dd37117dba5fe27b5323b82dfedef 100644
Kmods SIG 9e3ffb
--- a/src/misc.c
Kmods SIG 9e3ffb
+++ b/src/misc.c
Kmods SIG 9e3ffb
@@ -172,6 +172,25 @@ void exfat_update_bh(struct buffer_head *bh, int sync)
Kmods SIG 9e3ffb
 		sync_dirty_buffer(bh);
Kmods SIG 9e3ffb
 }
Kmods SIG 9e3ffb
 
Kmods SIG 9e3ffb
+int exfat_update_bhs(struct buffer_head **bhs, int nr_bhs, int sync)
Kmods SIG 9e3ffb
+{
Kmods SIG 9e3ffb
+	int i, err = 0;
Kmods SIG 9e3ffb
+
Kmods SIG 9e3ffb
+	for (i = 0; i < nr_bhs; i++) {
Kmods SIG 9e3ffb
+		set_buffer_uptodate(bhs[i]);
Kmods SIG 9e3ffb
+		mark_buffer_dirty(bhs[i]);
Kmods SIG 9e3ffb
+		if (sync)
Kmods SIG 9e3ffb
+			write_dirty_buffer(bhs[i], 0);
Kmods SIG 9e3ffb
+	}
Kmods SIG 9e3ffb
+
Kmods SIG 9e3ffb
+	for (i = 0; i < nr_bhs && sync; i++) {
Kmods SIG 9e3ffb
+		wait_on_buffer(bhs[i]);
Kmods SIG 9e3ffb
+		if (!err && !buffer_uptodate(bhs[i]))
Kmods SIG 9e3ffb
+			err = -EIO;
Kmods SIG 9e3ffb
+	}
Kmods SIG 9e3ffb
+	return err;
Kmods SIG 9e3ffb
+}
Kmods SIG 9e3ffb
+
Kmods SIG 9e3ffb
 void exfat_chain_set(struct exfat_chain *ec, unsigned int dir,
Kmods SIG 9e3ffb
 		unsigned int size, unsigned char flags)
Kmods SIG 9e3ffb
 {
Kmods SIG 9e3ffb
-- 
Kmods SIG 9e3ffb
2.31.1
Kmods SIG 9e3ffb