Skip to contentSkip to conversation

f2fs: reduce the number of inline_data inode before clearing it

PATCH New Jaegeuk Kim 1 participant 3 messages Nov 14, 2014

Subsystems (2)
lore
Share & tools
lore

Jaegeuk Kim

author maintainer
#0 lore raw

PATCH 1/3 f2fs: reduce the number of inline_data inode before clearing it

The # of inline_data inode is decreased only when it has inline_data. After clearing the flag, we can't decreased the number.

---
 fs/f2fs/inline.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)
fs/f2fs/inline.c +1 -1
index 8b66109..2310670 100644
@@ -116,8 +116,8 @@ no_update:
 	/* clear inline data and flag after data writeback */
 	truncate_inline_data(dn->inode_page, 0);
 clear_out:
-	f2fs_clear_inline_inode(dn->inode);
 	stat_dec_inline_inode(dn->inode);
+	f2fs_clear_inline_inode(dn->inode);
 	sync_inode_page(dn);
 	f2fs_put_dnode(dn);
 	return 0;
Signature · 9 lines
2.1.1


------------------------------------------------------------------------------
Comprehensive Server Monitoring with Site24x7.
Monitor 10 servers for $9/Month.
Get alerted through email, SMS, voice calls or mobile push notifications.
Take corrective actions from your mobile device.
http://pubads.g.doubleclick.net/gampad/clk?id=154624111&iu=/4140/ostg.clktrk
author maintainer
#1 lore raw

PATCH 2/3 f2fs: fix deadlock to grab 0'th data page

The scenario is like this.

One trhead triggers:
f2fs_write_data_pages
lock_page
f2fs_write_data_page
f2fs_lock_op <- wait

The other thread triggers:
f2fs_truncate
truncate_blocks
f2fs_lock_op
truncate_partial_data_page
lock_page <- wait for locking the page

This patch resolves this bug by relocating truncate_partial_data_page. This function is just to truncate user data page and not related to FS consistency as well.
And, we don't need to call truncate_inline_data. Rather than that, f2fs_write_data_page will finally update inline_data later.

---
 fs/f2fs/file.c | 8 +++-----
 1 file changed, 3 insertions(+), 5 deletions(-)
fs/f2fs/file.c +3 -5
index 54722a0..edc3ce8 100644
@@ -477,8 +477,6 @@ int truncate_blocks(struct inode *inode, u64 from, bool lock)
 	}
 
 	if (f2fs_has_inline_data(inode)) {
-		truncate_inline_data(ipage, from);
-		update_inode(inode, ipage);
 		f2fs_put_page(ipage, 1);
 		goto out;
 	}
@@ -504,13 +502,13 @@ int truncate_blocks(struct inode *inode, u64 from, bool lock)
 	f2fs_put_dnode(&dn);
 free_next:
 	err = truncate_inode_blocks(inode, free_from);
+out:
+	if (lock)
+		f2fs_unlock_op(sbi);
 
 	/* lastly zero out the first data page */
 	if (!err)
 		err = truncate_partial_data_page(inode, from);
-out:
-	if (lock)
-		f2fs_unlock_op(sbi);
 
 	trace_f2fs_truncate_blocks_exit(inode, err);
 	return err;
Signature · 9 lines
2.1.1


------------------------------------------------------------------------------
Comprehensive Server Monitoring with Site24x7.
Monitor 10 servers for $9/Month.
Get alerted through email, SMS, voice calls or mobile push notifications.
Take corrective actions from your mobile device.
http://pubads.g.doubleclick.net/gampad/clk?id=154624111&iu=/4140/ostg.clktrk
author maintainer
#2 lore raw

PATCH 3/3 f2fs: convert inline_data when i_size becomes large

In reply to Jaegeuk Kim

If i_size becomes large outside of MAX_INLINE_DATA, we shoud convert the inode. Otherwise, we can make some dirty pages during the truncation, and those pages will be written through f2fs_write_data_page.
At that moment, the inode has still inline_data, so that it tries to write non- zero pages into inline_data area.

---
 fs/f2fs/file.c   | 6 ++++++
 fs/f2fs/inline.c | 3 +++
 2 files changed, 9 insertions(+)
fs/f2fs/file.c +6 -0
index edc3ce8..7c2ec3e 100644
@@ -522,6 +522,12 @@ void f2fs_truncate(struct inode *inode)
 
 	trace_f2fs_truncate(inode);
 
+	/* we should check inline_data size */
+	if (f2fs_has_inline_data(inode) && !f2fs_may_inline(inode)) {
+		if (f2fs_convert_inline_inode(inode))
+			return;
+	}
+
 	if (!truncate_blocks(inode, i_size_read(inode), true)) {
 		inode->i_mtime = inode->i_ctime = CURRENT_TIME;
 		mark_inode_dirty(inode);
fs/f2fs/inline.c +3 -0
index 2310670..053d114 100644
@@ -24,6 +24,9 @@ bool f2fs_may_inline(struct inode *inode)
 	if (!S_ISREG(inode->i_mode))
 		return false;
 
+	if (i_size_read(inode) > MAX_INLINE_DATA)
+		return false;
+
 	return true;
 }
 
Signature · 9 lines
2.1.1


------------------------------------------------------------------------------
Comprehensive Server Monitoring with Site24x7.
Monitor 10 servers for $9/Month.
Get alerted through email, SMS, voice calls or mobile push notifications.
Take corrective actions from your mobile device.
http://pubads.g.doubleclick.net/gampad/clk?id=154624111&iu=/4140/ostg.clktrk