lkml.org 
[lkml]   [2004]   [Dec]   [25]   [last100]   RSS Feed
Views: [more markup]  [less markup]  [headers]  [forward] 
 
Messages in this thread
/
From"Hao-Ran Liu" <>
Subjectsys_fsync() and sys_sync() question
DateSat, 25 Dec 2004 18:04:54 +0800
Dear All,

I read kernel 2.6.9 page cache code and have some questions.
Please help ..

1. Why should sys_fsync() call filemap_fdatawrite()? Isn't it redundant in
kernel 2.6?
   since do_writepages() -> mpage_writepages() will walk the list of dirty
pages of the
   given address space and writepage() all of them, and, both
filemap_fdatawrite() and
   file->f_op->fsync() (ext2, for example) eventually call do_writepages()
function.

-----------------------------
asmlinkage long sys_fsync(unsigned int fd)
{
	struct file * file;
	struct address_space *mapping;
	int ret, err;
	ret = -EBADF;
	file = fget(fd);
	if (!file)
		goto out;
	mapping = file->f_mapping;

	ret = -EINVAL;
	if (!file->f_op || !file->f_op->fsync) {
		/* Why?  We can still call filemap_fdatawrite */
		goto out_putf;
	}
	/* We need to protect against concurrent writers.. */
	down(&mapping->host->i_sem);
	current->flags |= PF_SYNCWRITE;
	ret = filemap_fdatawrite(mapping);
	err = file->f_op->fsync(file, file->f_dentry, 0);
	if (!ret)
		ret = err;
	err = filemap_fdatawait(mapping);
	if (!ret)
		ret = err;
	current->flags &= ~PF_SYNCWRITE;
	up(&mapping->host->i_sem);
out_putf:
	fput(file);
out:
	return ret;
}
-----------------------------

2. for ext2, the purpose of sync_mapping_buffers() is to write out all
indirect blocks of 
   an address_space, which is called by ext2_sync_file()<-sys_fsync(). How
do these 
   buffers got sync'ed at sys_sync()? I don't find code writing out these
private buffers.
   If sync_mapping_buffers() is not needed for sys_sync(), then this should
apply for 
   ext2_sync_file().

-----------------------------
int ext2_sync_file(struct file *file, struct dentry *dentry, int datasync)
{
	struct inode *inode = dentry->d_inode;
	int err;
	int ret;
	ret = sync_mapping_buffers(inode->i_mapping);
	if (!(inode->i_state & I_DIRTY))
		return ret;
	if (datasync && !(inode->i_state & I_DIRTY_DATASYNC))
		return ret;
	err = ext2_sync_inode(inode);
	if (ret == 0)
		ret = err;
	return ret;
}
static void do_sync(unsigned long wait)
{
	wakeup_bdflush(0);
	sync_inodes(0);		/* All mappings, inodes and their blockdevs
*/
	DQUOT_SYNC(NULL);
	sync_supers();		/* Write the superblocks */
	sync_filesystems(0);	/* Start syncing the filesystems */
	sync_filesystems(wait);	/* Waitingly sync the filesystems */
	sync_inodes(wait);	/* Mappings, inodes and blockdevs, again. */
	if (!wait)
		printk("Emergency Sync complete\n");
	if (unlikely(laptop_mode))
		laptop_sync_completion();
}
asmlinkage long sys_sync(void)
{
	do_sync(1);
	return 0;
}
-----------------------------


Thank you,
Hao-Ran Liu





-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

\
 
 \ /
  Last update: 2005-03-22 14:09    [from the cache]
©2003-2008