lists.openwall.net   lists  /  announce  owl-users  owl-dev  john-users  john-dev  passwdqc-users  yescrypt  popa3d-users  /  oss-security  kernel-hardening  musl  sabotage  tlsify  passwords  /  crypt-dev  xvendor  /  Bugtraq  Full-Disclosure  linux-kernel  linux-netdev  linux-ext4  linux-hardening  linux-cve-announce  PHC 
Open Source and information security mailing list archives
 
Hash Suite: Windows password security audit tool. GUI, reports in PDF.
[<prev] [next>] [day] [month] [year] [list]
Message-Id: <20250723084955.547901-1-liaoyuanhong@vivo.com>
Date: Wed, 23 Jul 2025 16:49:55 +0800
From: Liao Yuanhong <liaoyuanhong@...o.com>
To: Jaegeuk Kim <jaegeuk@...nel.org>,
	Chao Yu <chao@...nel.org>
Cc: linux-f2fs-devel@...ts.sourceforge.net,
	linux-kernel@...r.kernel.org,
	Liao Yuanhong <liaoyuanhong@...o.com>
Subject: [PATCH] f2fs:Add adjustable write endpoints for multiple devices

During the development process, we encounter the following two issues:

1.In a multi-device scenario, it's likely that two devices exhibit
inconsistent performance, causing fluctuations in performance and making
usage and testing inconvenient. Under normal circumstances, we hope to
prioritize the use of the device with better performance and consider the
device with poorer performance when space is insufficient. Using reuse
mode can solve some of the issues, but tests reveal that the fragmentation
degree in reuse mode is significantly higher than in default mode, which
poses performance risks.

2.We need to examine the differences in data placement for different sizes
of storage devices under specific write patterns. Currently, this
comparison can only be made by switching storage devices.

To address the above issues, I am considering adding a last_secno node. By
adjusting this node, we can change the end of the addressing in
get_new_segment so that it readdresses from 0 once the set value is
reached. The default value of the node is the maximum number of sections
for the current storage device, so making no modifications will not affect
the current logic. If the space before the set value is already filled with
valid data, it will normally write into the free area after the set value.

Signed-off-by: Liao Yuanhong <liaoyuanhong@...o.com>
---
 Documentation/ABI/testing/sysfs-fs-f2fs | 8 ++++++++
 fs/f2fs/f2fs.h                          | 1 +
 fs/f2fs/segment.c                       | 4 ++--
 fs/f2fs/super.c                         | 1 +
 fs/f2fs/sysfs.c                         | 9 +++++++++
 5 files changed, 21 insertions(+), 2 deletions(-)

diff --git a/Documentation/ABI/testing/sysfs-fs-f2fs b/Documentation/ABI/testing/sysfs-fs-f2fs
index c2a233f2a085..e5ad8dc70cb6 100644
--- a/Documentation/ABI/testing/sysfs-fs-f2fs
+++ b/Documentation/ABI/testing/sysfs-fs-f2fs
@@ -870,3 +870,11 @@ Description:	This threshold is used to control triggering garbage collection whi
 		reserved section before preallocating on pinned file.
 		By default, the value is ovp_sections, especially, for zoned ufs, the
 		value is 1.
+
+What:		/sys/fs/f2fs/<disk>/last_secno
+Date:		July 2025
+Contact:	"Yuanhong Liao" <liaoyuanhong@...o.com>
+Description:	This node is used to adjust the addressing end of f2fs when writing.
+		The default value is the maximum number of sections in the storage. If the
+		frontend space is full after adjusting the address, it will still address to
+		the back of the address until reaching the end of the memory.
\ No newline at end of file
diff --git a/fs/f2fs/f2fs.h b/fs/f2fs/f2fs.h
index e6dcd7e6f47c..7d93d8671033 100644
--- a/fs/f2fs/f2fs.h
+++ b/fs/f2fs/f2fs.h
@@ -1802,6 +1802,7 @@ struct f2fs_sb_info {
 	spinlock_t dev_lock;			/* protect dirty_device */
 	bool aligned_blksize;			/* all devices has the same logical blksize */
 	unsigned int first_seq_zone_segno;	/* first segno in sequential zone */
+	unsigned int last_secno;		/* for adjust the end of target device */
 
 	/* For write statistics */
 	u64 sectors_written_start;
diff --git a/fs/f2fs/segment.c b/fs/f2fs/segment.c
index cc82d42ef14c..192619bb2034 100644
--- a/fs/f2fs/segment.c
+++ b/fs/f2fs/segment.c
@@ -2811,7 +2811,7 @@ static int get_new_segment(struct f2fs_sb_info *sbi,
 	secno = find_next_zero_bit(free_i->free_secmap, MAIN_SECS(sbi), hint);
 
 #ifdef CONFIG_BLK_DEV_ZONED
-	if (secno >= MAIN_SECS(sbi) && f2fs_sb_has_blkzoned(sbi)) {
+	if (secno >= sbi->last_secno && f2fs_sb_has_blkzoned(sbi)) {
 		/* Write only to sequential zones */
 		if (sbi->blkzone_alloc_policy == BLKZONE_ALLOC_ONLY_SEQ) {
 			hint = GET_SEC_FROM_SEG(sbi, sbi->first_seq_zone_segno);
@@ -2827,7 +2827,7 @@ static int get_new_segment(struct f2fs_sb_info *sbi,
 	}
 #endif
 
-	if (secno >= MAIN_SECS(sbi)) {
+	if (secno >= sbi->last_secno) {
 		secno = find_first_zero_bit(free_i->free_secmap,
 							MAIN_SECS(sbi));
 		if (secno >= MAIN_SECS(sbi)) {
diff --git a/fs/f2fs/super.c b/fs/f2fs/super.c
index 30c038413040..5b7de0734da7 100644
--- a/fs/f2fs/super.c
+++ b/fs/f2fs/super.c
@@ -3859,6 +3859,7 @@ static int sanity_check_raw_super(struct f2fs_sb_info *sbi,
 	segs_per_sec = le32_to_cpu(raw_super->segs_per_sec);
 	secs_per_zone = le32_to_cpu(raw_super->secs_per_zone);
 	total_sections = le32_to_cpu(raw_super->section_count);
+	sbi->last_secno = total_sections;
 
 	/* blocks_per_seg should be 512, given the above check */
 	blocks_per_seg = BIT(le32_to_cpu(raw_super->log_blocks_per_seg));
diff --git a/fs/f2fs/sysfs.c b/fs/f2fs/sysfs.c
index bdef926b3377..a4ab5c38e883 100644
--- a/fs/f2fs/sysfs.c
+++ b/fs/f2fs/sysfs.c
@@ -649,6 +649,13 @@ static ssize_t __sbi_store(struct f2fs_attr *a,
 		return count;
 	}
 
+	if (!strcmp(a->attr.name, "last_secno")) {
+		if (t < 0 || t > MAIN_SECS(sbi))
+			return -EINVAL;
+		sbi->last_secno = t;
+		return count;
+	}
+
 #ifdef CONFIG_F2FS_IOSTAT
 	if (!strcmp(a->attr.name, "iostat_enable")) {
 		sbi->iostat_enable = !!t;
@@ -1122,6 +1129,7 @@ F2FS_SBI_GENERAL_RW_ATTR(max_victim_search);
 F2FS_SBI_GENERAL_RW_ATTR(migration_granularity);
 F2FS_SBI_GENERAL_RW_ATTR(migration_window_granularity);
 F2FS_SBI_GENERAL_RW_ATTR(dir_level);
+F2FS_SBI_GENERAL_RW_ATTR(last_secno);
 #ifdef CONFIG_F2FS_IOSTAT
 F2FS_SBI_GENERAL_RW_ATTR(iostat_enable);
 F2FS_SBI_GENERAL_RW_ATTR(iostat_period_ms);
@@ -1285,6 +1293,7 @@ static struct attribute *f2fs_attrs[] = {
 	ATTR_LIST(discard_idle_interval),
 	ATTR_LIST(gc_idle_interval),
 	ATTR_LIST(umount_discard_timeout),
+	ATTR_LIST(last_secno),
 #ifdef CONFIG_F2FS_IOSTAT
 	ATTR_LIST(iostat_enable),
 	ATTR_LIST(iostat_period_ms),
-- 
2.34.1


Powered by blists - more mailing lists

Powered by Openwall GNU/*/Linux Powered by OpenVZ