f2fs: check curseg space before foreground GC
When we are closing to trigger foreground GC, if there are only a few of dirty metas, we can log these dirty metas in left space of opened segments instead of triggering foreground GC. With this patch, total count of foreground GC triggered by test/generic/* of fstest suit reduce from 254 to 184. So let's do the check before foreground GC anyway. Signed-off-by: Chao Yu <yuchao0@huawei.com> Signed-off-by: Jaegeuk Kim <jaegeuk@kernel.org>
This commit is contained in:
parent
3d26fa6be3
commit
bf34c93d26
|
@ -497,6 +497,33 @@ static inline int reserved_sections(struct f2fs_sb_info *sbi)
|
|||
return GET_SEC_FROM_SEG(sbi, (unsigned int)reserved_segments(sbi));
|
||||
}
|
||||
|
||||
static inline bool has_curseg_enough_space(struct f2fs_sb_info *sbi)
|
||||
{
|
||||
unsigned int node_blocks = get_pages(sbi, F2FS_DIRTY_NODES) +
|
||||
get_pages(sbi, F2FS_DIRTY_DENTS);
|
||||
unsigned int dent_blocks = get_pages(sbi, F2FS_DIRTY_DENTS);
|
||||
unsigned int segno, left_blocks;
|
||||
int i;
|
||||
|
||||
/* check current node segment */
|
||||
for (i = CURSEG_HOT_NODE; i <= CURSEG_COLD_NODE; i++) {
|
||||
segno = CURSEG_I(sbi, i)->segno;
|
||||
left_blocks = sbi->blocks_per_seg -
|
||||
get_seg_entry(sbi, segno)->ckpt_valid_blocks;
|
||||
|
||||
if (node_blocks > left_blocks)
|
||||
return false;
|
||||
}
|
||||
|
||||
/* check current data segment */
|
||||
segno = CURSEG_I(sbi, CURSEG_HOT_DATA)->segno;
|
||||
left_blocks = sbi->blocks_per_seg -
|
||||
get_seg_entry(sbi, segno)->ckpt_valid_blocks;
|
||||
if (dent_blocks > left_blocks)
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
static inline bool has_not_enough_free_secs(struct f2fs_sb_info *sbi,
|
||||
int freed, int needed)
|
||||
{
|
||||
|
@ -507,6 +534,9 @@ static inline bool has_not_enough_free_secs(struct f2fs_sb_info *sbi,
|
|||
if (unlikely(is_sbi_flag_set(sbi, SBI_POR_DOING)))
|
||||
return false;
|
||||
|
||||
if (free_sections(sbi) + freed == reserved_sections(sbi) + needed &&
|
||||
has_curseg_enough_space(sbi))
|
||||
return false;
|
||||
return (free_sections(sbi) + freed) <=
|
||||
(node_secs + 2 * dent_secs + imeta_secs +
|
||||
reserved_sections(sbi) + needed);
|
||||
|
|
Loading…
Reference in New Issue