Skip to content

Commit d46dd0d

Browse files
committed
Merge tag 'f2fs-for-7.1-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/jaegeuk/f2fs
Pull f2fs updates from Jaegeuk Kim: "In this round, the changes primarily focus on resolving race conditions, memory safety issues (UAF), and improving the robustness of garbage collection (GC), and folio management. Enhancements: - add page-order information for large folio reads in iostat - add defrag_blocks sysfs node Bug fixes: - fix uninitialized kobject put in f2fs_init_sysfs() - disallow setting an extension to both cold and hot - fix node_cnt race between extent node destroy and writeback - preserve previous reserve_{blocks,node} value when remount - freeze GC and discard threads quickly - fix false alarm of lockdep on cp_global_sem lock - fix data loss caused by incorrect use of nat_entry flag - skip empty sections in f2fs_get_victim - fix inline data not being written to disk in writeback path - fix fsck inconsistency caused by FGGC of node block - fix fsck inconsistency caused by incorrect nat_entry flag usage - call f2fs_handle_critical_error() to set cp_error flag - fix fiemap boundary handling when read extent cache is incomplete - fix use-after-free of sbi in f2fs_compress_write_end_io() - fix UAF caused by decrementing sbi->nr_pages[] in f2fs_write_end_io() - fix incorrect file address mapping when inline inode is unwritten - fix incomplete search range in f2fs_get_victim when f2fs_need_rand_seg is enabled - avoid memory leak in f2fs_rename()" * tag 'f2fs-for-7.1-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/jaegeuk/f2fs: (35 commits) f2fs: add page-order information for large folio reads in iostat f2fs: do not support mmap write for large folio f2fs: fix uninitialized kobject put in f2fs_init_sysfs() f2fs: protect extension_list reading with sb_lock in f2fs_sbi_show() f2fs: disallow setting an extension to both cold and hot f2fs: fix node_cnt race between extent node destroy and writeback f2fs: allow empty mount string for Opt_usr|grp|projjquota f2fs: fix to preserve previous reserve_{blocks,node} value when remount f2fs: invalidate block device page cache on umount f2fs: fix to freeze GC and discard threads quickly f2fs: fix to avoid uninit-value access in f2fs_sanity_check_node_footer f2fs: fix false alarm of lockdep on cp_global_sem lock f2fs: fix data loss caused by incorrect use of nat_entry flag f2fs: fix to skip empty sections in f2fs_get_victim f2fs: fix inline data not being written to disk in writeback path f2fs: fix fsck inconsistency caused by FGGC of node block f2fs: fix fsck inconsistency caused by incorrect nat_entry flag usage f2fs: fix to do sanity check on dcc->discard_cmd_cnt conditionally f2fs: refactor node footer flag setting related code f2fs: refactor f2fs_move_node_folio function ...
2 parents bb0bc49 + cb8ff3e commit d46dd0d

21 files changed

Lines changed: 386 additions & 151 deletions

File tree

Documentation/ABI/testing/sysfs-fs-f2fs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -407,6 +407,12 @@ Contact: "Hridya Valsaraju" <[email protected]>
407407
Description: Average number of valid blocks.
408408
Available when CONFIG_F2FS_STAT_FS=y.
409409

410+
What: /sys/fs/f2fs/<disk>/defrag_blocks
411+
Date: February 2026
412+
Contact: "Jinbao Liu" <[email protected]>
413+
Description: Number of blocks moved by defragment.
414+
Available when CONFIG_F2FS_STAT_FS=y.
415+
410416
What: /sys/fs/f2fs/<disk>/mounted_time_sec
411417
Date: February 2020
412418
Contact: "Jaegeuk Kim" <[email protected]>

fs/f2fs/checkpoint.c

Lines changed: 0 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -232,15 +232,6 @@ static inline void f2fs_unlock_all(struct f2fs_sb_info *sbi)
232232
static struct kmem_cache *ino_entry_slab;
233233
struct kmem_cache *f2fs_inode_entry_slab;
234234

235-
void f2fs_stop_checkpoint(struct f2fs_sb_info *sbi, bool end_io,
236-
unsigned char reason)
237-
{
238-
f2fs_build_fault_attr(sbi, 0, 0, FAULT_ALL);
239-
if (!end_io)
240-
f2fs_flush_merged_writes(sbi);
241-
f2fs_handle_critical_error(sbi, reason);
242-
}
243-
244235
/*
245236
* We guarantee no failure on the returned page.
246237
*/

fs/f2fs/compress.c

Lines changed: 11 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1491,10 +1491,10 @@ void f2fs_compress_write_end_io(struct bio *bio, struct folio *folio)
14911491

14921492
f2fs_compress_free_page(page);
14931493

1494-
dec_page_count(sbi, type);
1495-
1496-
if (atomic_dec_return(&cic->pending_pages))
1494+
if (atomic_dec_return(&cic->pending_pages)) {
1495+
dec_page_count(sbi, type);
14971496
return;
1497+
}
14981498

14991499
for (i = 0; i < cic->nr_rpages; i++) {
15001500
WARN_ON(!cic->rpages[i]);
@@ -1504,6 +1504,14 @@ void f2fs_compress_write_end_io(struct bio *bio, struct folio *folio)
15041504

15051505
page_array_free(sbi, cic->rpages, cic->nr_rpages);
15061506
kmem_cache_free(cic_entry_slab, cic);
1507+
1508+
/*
1509+
* Make sure dec_page_count() is the last access to sbi.
1510+
* Once it drops the F2FS_WB_CP_DATA counter to zero, the
1511+
* unmount thread can proceed to destroy sbi and
1512+
* sbi->page_array_slab.
1513+
*/
1514+
dec_page_count(sbi, type);
15071515
}
15081516

15091517
static int f2fs_write_raw_pages(struct compress_ctx *cc,

fs/f2fs/data.c

Lines changed: 34 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -173,7 +173,8 @@ static void f2fs_finish_read_bio(struct bio *bio, bool in_task)
173173
while (nr_pages--)
174174
dec_page_count(F2FS_F_SB(folio), __read_io_type(folio));
175175

176-
if (F2FS_F_SB(folio)->node_inode && is_node_folio(folio) &&
176+
if (bio->bi_status == BLK_STS_OK &&
177+
F2FS_F_SB(folio)->node_inode && is_node_folio(folio) &&
177178
f2fs_sanity_check_node_footer(F2FS_F_SB(folio),
178179
folio, folio->index, NODE_TYPE_REGULAR, true))
179180
bio->bi_status = BLK_STS_IOERR;
@@ -386,6 +387,8 @@ static void f2fs_write_end_io(struct bio *bio)
386387
folio->index, NODE_TYPE_REGULAR, true);
387388
f2fs_bug_on(sbi, folio->index != nid_of_node(folio));
388389
}
390+
if (f2fs_in_warm_node_list(folio))
391+
f2fs_del_fsync_node_entry(sbi, folio);
389392

390393
dec_page_count(sbi, type);
391394

@@ -397,8 +400,6 @@ static void f2fs_write_end_io(struct bio *bio)
397400
wq_has_sleeper(&sbi->cp_wait))
398401
wake_up(&sbi->cp_wait);
399402

400-
if (f2fs_in_warm_node_list(sbi, folio))
401-
f2fs_del_fsync_node_entry(sbi, folio);
402403
folio_clear_f2fs_gcing(folio);
403404
folio_end_writeback(folio);
404405
}
@@ -1578,7 +1579,8 @@ static bool f2fs_map_blocks_cached(struct inode *inode,
15781579
f2fs_wait_on_block_writeback_range(inode,
15791580
map->m_pblk, map->m_len);
15801581

1581-
if (f2fs_allow_multi_device_dio(sbi, flag)) {
1582+
map->m_multidev_dio = f2fs_allow_multi_device_dio(sbi, flag);
1583+
if (map->m_multidev_dio) {
15821584
int bidx = f2fs_target_device_index(sbi, map->m_pblk);
15831585
struct f2fs_dev_info *dev = &sbi->devs[bidx];
15841586

@@ -1638,8 +1640,26 @@ int f2fs_map_blocks(struct inode *inode, struct f2fs_map_blocks *map, int flag)
16381640
lfs_dio_write = (flag == F2FS_GET_BLOCK_DIO && f2fs_lfs_mode(sbi) &&
16391641
map->m_may_create);
16401642

1641-
if (!map->m_may_create && f2fs_map_blocks_cached(inode, map, flag))
1642-
goto out;
1643+
if (!map->m_may_create && f2fs_map_blocks_cached(inode, map, flag)) {
1644+
struct extent_info ei;
1645+
1646+
/*
1647+
* 1. If map->m_multidev_dio is true, map->m_pblk cannot be
1648+
* waitted by f2fs_wait_on_block_writeback_range() and are not
1649+
* mergeable.
1650+
* 2. If pgofs hits the read extent cache, it means the mapping
1651+
* is already cached in the extent cache, but it is not
1652+
* mergeable, and there is no need to query the mapping again
1653+
* via f2fs_get_dnode_of_data().
1654+
*/
1655+
pgofs = (pgoff_t)map->m_lblk + map->m_len;
1656+
if (map->m_len == maxblocks ||
1657+
map->m_multidev_dio ||
1658+
f2fs_lookup_read_extent_cache(inode, pgofs, &ei))
1659+
goto out;
1660+
ofs = map->m_len;
1661+
goto map_more;
1662+
}
16431663

16441664
map->m_bdev = inode->i_sb->s_bdev;
16451665
map->m_multidev_dio =
@@ -1650,7 +1670,8 @@ int f2fs_map_blocks(struct inode *inode, struct f2fs_map_blocks *map, int flag)
16501670

16511671
/* it only supports block size == page size */
16521672
pgofs = (pgoff_t)map->m_lblk;
1653-
end = pgofs + maxblocks;
1673+
map_more:
1674+
end = (pgoff_t)map->m_lblk + maxblocks;
16541675

16551676
if (flag == F2FS_GET_BLOCK_PRECACHE)
16561677
mode = LOOKUP_NODE_RA;
@@ -2490,6 +2511,8 @@ static int f2fs_read_data_large_folio(struct inode *inode,
24902511
if (!folio)
24912512
goto out;
24922513

2514+
f2fs_update_read_folio_count(F2FS_I_SB(inode), folio);
2515+
24932516
folio_in_bio = false;
24942517
index = folio->index;
24952518
offset = 0;
@@ -2664,6 +2687,8 @@ static int f2fs_mpage_readpages(struct inode *inode, struct fsverity_info *vi,
26642687
prefetchw(&folio->flags);
26652688
}
26662689

2690+
f2fs_update_read_folio_count(F2FS_I_SB(inode), folio);
2691+
26672692
#ifdef CONFIG_F2FS_FS_COMPRESSION
26682693
index = folio->index;
26692694

@@ -2790,7 +2815,6 @@ int f2fs_encrypt_one_page(struct f2fs_io_info *fio)
27902815
struct inode *inode = fio_inode(fio);
27912816
struct folio *mfolio;
27922817
struct page *page;
2793-
gfp_t gfp_flags = GFP_NOFS;
27942818

27952819
if (!f2fs_encrypted_file(inode))
27962820
return 0;
@@ -2800,19 +2824,10 @@ int f2fs_encrypt_one_page(struct f2fs_io_info *fio)
28002824
if (fscrypt_inode_uses_inline_crypto(inode))
28012825
return 0;
28022826

2803-
retry_encrypt:
28042827
fio->encrypted_page = fscrypt_encrypt_pagecache_blocks(page_folio(page),
2805-
PAGE_SIZE, 0, gfp_flags);
2806-
if (IS_ERR(fio->encrypted_page)) {
2807-
/* flush pending IOs and wait for a while in the ENOMEM case */
2808-
if (PTR_ERR(fio->encrypted_page) == -ENOMEM) {
2809-
f2fs_flush_merged_writes(fio->sbi);
2810-
memalloc_retry_wait(GFP_NOFS);
2811-
gfp_flags |= __GFP_NOFAIL;
2812-
goto retry_encrypt;
2813-
}
2828+
PAGE_SIZE, 0, GFP_NOFS);
2829+
if (IS_ERR(fio->encrypted_page))
28142830
return PTR_ERR(fio->encrypted_page);
2815-
}
28162831

28172832
mfolio = filemap_lock_folio(META_MAPPING(fio->sbi), fio->old_blkaddr);
28182833
if (!IS_ERR(mfolio)) {

fs/f2fs/debug.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -659,6 +659,7 @@ static int stat_show(struct seq_file *s, void *v)
659659
si->bg_node_blks);
660660
seq_printf(s, "BG skip : IO: %u, Other: %u\n",
661661
si->io_skip_bggc, si->other_skip_bggc);
662+
seq_printf(s, "defrag blocks : %u\n", si->defrag_blks);
662663
seq_puts(s, "\nExtent Cache (Read):\n");
663664
seq_printf(s, " - Hit Count: L1-1:%llu L1-2:%llu L2:%llu\n",
664665
si->hit_largest, si->hit_cached[EX_READ],

fs/f2fs/extent_cache.c

Lines changed: 10 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -119,9 +119,10 @@ static bool __may_extent_tree(struct inode *inode, enum extent_type type)
119119
if (!__init_may_extent_tree(inode, type))
120120
return false;
121121

122+
if (is_inode_flag_set(inode, FI_NO_EXTENT))
123+
return false;
124+
122125
if (type == EX_READ) {
123-
if (is_inode_flag_set(inode, FI_NO_EXTENT))
124-
return false;
125126
if (is_inode_flag_set(inode, FI_COMPRESSED_FILE) &&
126127
!f2fs_sb_has_readonly(F2FS_I_SB(inode)))
127128
return false;
@@ -644,6 +645,8 @@ static unsigned int __destroy_extent_node(struct inode *inode,
644645

645646
while (atomic_read(&et->node_cnt)) {
646647
write_lock(&et->lock);
648+
if (!is_inode_flag_set(inode, FI_NO_EXTENT))
649+
set_inode_flag(inode, FI_NO_EXTENT);
647650
node_cnt += __free_extent_tree(sbi, et, nr_shrink);
648651
write_unlock(&et->lock);
649652
}
@@ -688,12 +691,12 @@ static void __update_extent_tree_range(struct inode *inode,
688691

689692
write_lock(&et->lock);
690693

691-
if (type == EX_READ) {
692-
if (is_inode_flag_set(inode, FI_NO_EXTENT)) {
693-
write_unlock(&et->lock);
694-
return;
695-
}
694+
if (is_inode_flag_set(inode, FI_NO_EXTENT)) {
695+
write_unlock(&et->lock);
696+
return;
697+
}
696698

699+
if (type == EX_READ) {
697700
prev = et->largest;
698701
dei.len = 0;
699702

fs/f2fs/f2fs.h

Lines changed: 35 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010

1111
#include <linux/uio.h>
1212
#include <linux/types.h>
13+
#include <linux/mmzone.h>
1314
#include <linux/page-flags.h>
1415
#include <linux/slab.h>
1516
#include <linux/crc32.h>
@@ -2032,6 +2033,8 @@ struct f2fs_sb_info {
20322033
unsigned long long iostat_count[NR_IO_TYPE];
20332034
unsigned long long iostat_bytes[NR_IO_TYPE];
20342035
unsigned long long prev_iostat_bytes[NR_IO_TYPE];
2036+
unsigned long long iostat_read_folio_count[NR_PAGE_ORDERS];
2037+
unsigned long long prev_iostat_read_folio_count[NR_PAGE_ORDERS];
20352038
bool iostat_enable;
20362039
unsigned long iostat_next_period;
20372040
unsigned int iostat_period_ms;
@@ -2040,6 +2043,9 @@ struct f2fs_sb_info {
20402043
spinlock_t iostat_lat_lock;
20412044
struct iostat_lat_info *iostat_io_lat;
20422045
#endif
2046+
#ifdef CONFIG_DEBUG_LOCK_ALLOC
2047+
struct lock_class_key cp_global_sem_key;
2048+
#endif
20432049
};
20442050

20452051
/* Definitions to access f2fs_sb_info */
@@ -3900,7 +3906,6 @@ int f2fs_do_quota_sync(struct super_block *sb, int type);
39003906
loff_t max_file_blocks(struct inode *inode);
39013907
void f2fs_quota_off_umount(struct super_block *sb);
39023908
void f2fs_save_errors(struct f2fs_sb_info *sbi, unsigned char flag);
3903-
void f2fs_handle_critical_error(struct f2fs_sb_info *sbi, unsigned char reason);
39043909
void f2fs_handle_error(struct f2fs_sb_info *sbi, unsigned char error);
39053910
int f2fs_commit_super(struct f2fs_sb_info *sbi, bool recover);
39063911
int f2fs_sync_fs(struct super_block *sb, int sync);
@@ -3919,11 +3924,11 @@ enum node_type;
39193924

39203925
int f2fs_check_nid_range(struct f2fs_sb_info *sbi, nid_t nid);
39213926
bool f2fs_available_free_memory(struct f2fs_sb_info *sbi, int type);
3922-
bool f2fs_in_warm_node_list(struct f2fs_sb_info *sbi, struct folio *folio);
3927+
bool f2fs_in_warm_node_list(struct folio *folio);
39233928
void f2fs_init_fsync_node_info(struct f2fs_sb_info *sbi);
39243929
void f2fs_del_fsync_node_entry(struct f2fs_sb_info *sbi, struct folio *folio);
39253930
void f2fs_reset_fsync_node_info(struct f2fs_sb_info *sbi);
3926-
int f2fs_need_dentry_mark(struct f2fs_sb_info *sbi, nid_t nid);
3931+
bool f2fs_need_dentry_mark(struct f2fs_sb_info *sbi, nid_t nid);
39273932
bool f2fs_is_checkpointed_node(struct f2fs_sb_info *sbi, nid_t nid);
39283933
bool f2fs_need_inode_block_update(struct f2fs_sb_info *sbi, nid_t ino);
39293934
int f2fs_get_node_info(struct f2fs_sb_info *sbi, nid_t nid,
@@ -3945,6 +3950,8 @@ int f2fs_sanity_check_node_footer(struct f2fs_sb_info *sbi,
39453950
enum node_type ntype, bool in_irq);
39463951
struct folio *f2fs_get_inode_folio(struct f2fs_sb_info *sbi, pgoff_t ino);
39473952
struct folio *f2fs_get_xnode_folio(struct f2fs_sb_info *sbi, pgoff_t xnid);
3953+
int f2fs_write_single_node_folio(struct folio *node_folio, int sync_mode,
3954+
bool mark_dirty, enum iostat_type io_type);
39483955
int f2fs_move_node_folio(struct folio *node_folio, int gc_type);
39493956
void f2fs_flush_inline_data(struct f2fs_sb_info *sbi);
39503957
int f2fs_fsync_node_pages(struct f2fs_sb_info *sbi, struct inode *inode,
@@ -3987,7 +3994,7 @@ bool f2fs_is_checkpointed_data(struct f2fs_sb_info *sbi, block_t blkaddr);
39873994
int f2fs_start_discard_thread(struct f2fs_sb_info *sbi);
39883995
void f2fs_drop_discard_cmd(struct f2fs_sb_info *sbi);
39893996
void f2fs_stop_discard_thread(struct f2fs_sb_info *sbi);
3990-
bool f2fs_issue_discard_timeout(struct f2fs_sb_info *sbi);
3997+
bool f2fs_issue_discard_timeout(struct f2fs_sb_info *sbi, bool need_check);
39913998
void f2fs_clear_prefree_segments(struct f2fs_sb_info *sbi,
39923999
struct cp_control *cpc);
39934000
void f2fs_dirty_to_prefree(struct f2fs_sb_info *sbi);
@@ -4286,6 +4293,7 @@ struct f2fs_stat_info {
42864293
int gc_secs[2][2];
42874294
int tot_blks, data_blks, node_blks;
42884295
int bg_data_blks, bg_node_blks;
4296+
unsigned int defrag_blks;
42894297
int blkoff[NR_CURSEG_TYPE];
42904298
int curseg[NR_CURSEG_TYPE];
42914299
int cursec[NR_CURSEG_TYPE];
@@ -4420,6 +4428,9 @@ static inline struct f2fs_stat_info *F2FS_STAT(struct f2fs_sb_info *sbi)
44204428
si->bg_node_blks += ((gc_type) == BG_GC) ? (blks) : 0; \
44214429
} while (0)
44224430

4431+
#define stat_inc_defrag_blk_count(sbi, blks) \
4432+
(F2FS_STAT(sbi)->defrag_blks += (blks))
4433+
44234434
int f2fs_build_stats(struct f2fs_sb_info *sbi);
44244435
void f2fs_destroy_stats(struct f2fs_sb_info *sbi);
44254436
void __init f2fs_create_root_stats(void);
@@ -4461,6 +4472,7 @@ void f2fs_update_sit_info(struct f2fs_sb_info *sbi);
44614472
#define stat_inc_tot_blk_count(si, blks) do { } while (0)
44624473
#define stat_inc_data_blk_count(sbi, blks, gc_type) do { } while (0)
44634474
#define stat_inc_node_blk_count(sbi, blks, gc_type) do { } while (0)
4475+
#define stat_inc_defrag_blk_count(sbi, blks) do { } while (0)
44644476

44654477
static inline int f2fs_build_stats(struct f2fs_sb_info *sbi) { return 0; }
44664478
static inline void f2fs_destroy_stats(struct f2fs_sb_info *sbi) { }
@@ -5063,8 +5075,25 @@ static inline void f2fs_handle_page_eio(struct f2fs_sb_info *sbi,
50635075
return;
50645076

50655077
if (ofs == sbi->page_eio_ofs[type]) {
5066-
if (sbi->page_eio_cnt[type]++ == MAX_RETRY_PAGE_EIO)
5067-
set_ckpt_flags(sbi, CP_ERROR_FLAG);
5078+
if (sbi->page_eio_cnt[type]++ == MAX_RETRY_PAGE_EIO) {
5079+
enum stop_cp_reason stop_reason;
5080+
5081+
switch (type) {
5082+
case META:
5083+
stop_reason = STOP_CP_REASON_READ_META;
5084+
break;
5085+
case NODE:
5086+
stop_reason = STOP_CP_REASON_READ_NODE;
5087+
break;
5088+
case DATA:
5089+
stop_reason = STOP_CP_REASON_READ_DATA;
5090+
break;
5091+
default:
5092+
f2fs_bug_on(sbi, 1);
5093+
return;
5094+
}
5095+
f2fs_stop_checkpoint(sbi, false, stop_reason);
5096+
}
50685097
} else {
50695098
sbi->page_eio_ofs[type] = ofs;
50705099
sbi->page_eio_cnt[type] = 0;

fs/f2fs/file.c

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -81,8 +81,17 @@ static vm_fault_t f2fs_vm_page_mkwrite(struct vm_fault *vmf)
8181
int err = 0;
8282
vm_fault_t ret;
8383

84-
if (unlikely(IS_IMMUTABLE(inode)))
84+
/*
85+
* We only support large folio on the read case.
86+
* Don't make any dirty pages.
87+
*/
88+
if (unlikely(IS_IMMUTABLE(inode)) ||
89+
mapping_large_folio_support(inode->i_mapping)) {
90+
f2fs_err(sbi, "Not expected: immutable: %d large_folio: %d",
91+
IS_IMMUTABLE(inode),
92+
mapping_large_folio_support(inode->i_mapping));
8593
return VM_FAULT_SIGBUS;
94+
}
8695

8796
if (is_inode_flag_set(inode, FI_COMPRESS_RELEASED)) {
8897
err = -EIO;
@@ -3042,8 +3051,10 @@ static int f2fs_defragment_range(struct f2fs_sb_info *sbi,
30423051
clear_inode_flag(inode, FI_OPU_WRITE);
30433052
unlock_out:
30443053
inode_unlock(inode);
3045-
if (!err)
3054+
if (!err) {
30463055
range->len = (u64)total << PAGE_SHIFT;
3056+
stat_inc_defrag_blk_count(sbi, total);
3057+
}
30473058
return err;
30483059
}
30493060

0 commit comments

Comments
 (0)