diff options
author | Jan Kara <jack@suse.cz> | 2008-07-25 04:46:36 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2008-07-25 13:53:33 -0400 |
commit | 5d4f7fddf8882b214e4aabb3bdb37f90a72b2537 (patch) | |
tree | b8cf1f13c1032367c0160722764adf1cbca9e92a | |
parent | 895c23f8c39c0c8d7b536bb2566d4aa968d78be2 (diff) |
reiserfs: fix synchronization of quota files in journal=data mode
In journal=data mode, it is not enough to do write_inode_now() as done in
vfs_quota_on() to write all data to their final location (which is needed for
quota_read to work correctly). Calling journal_end_sync() before calling
vfs_quota_on() does it's job because transactions are committed to the journal
and data marked as dirty in memory so write_inode_now() writes them to their
final locations.
Cc: <reiserfs-devel@vger.kernel.org>
Signed-off-by: Jan Kara <jack@suse.cz>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
-rw-r--r-- | fs/reiserfs/super.c | 30 |
1 files changed, 21 insertions, 9 deletions
diff --git a/fs/reiserfs/super.c b/fs/reiserfs/super.c index 1d40f2bd1970..0cbf4cd11147 100644 --- a/fs/reiserfs/super.c +++ b/fs/reiserfs/super.c | |||
@@ -2026,6 +2026,7 @@ static int reiserfs_quota_on(struct super_block *sb, int type, int format_id, | |||
2026 | int err; | 2026 | int err; |
2027 | struct nameidata nd; | 2027 | struct nameidata nd; |
2028 | struct inode *inode; | 2028 | struct inode *inode; |
2029 | struct reiserfs_transaction_handle th; | ||
2029 | 2030 | ||
2030 | if (!(REISERFS_SB(sb)->s_mount_opt & (1 << REISERFS_QUOTA))) | 2031 | if (!(REISERFS_SB(sb)->s_mount_opt & (1 << REISERFS_QUOTA))) |
2031 | return -EINVAL; | 2032 | return -EINVAL; |
@@ -2053,17 +2054,28 @@ static int reiserfs_quota_on(struct super_block *sb, int type, int format_id, | |||
2053 | } | 2054 | } |
2054 | mark_inode_dirty(inode); | 2055 | mark_inode_dirty(inode); |
2055 | } | 2056 | } |
2056 | /* Not journalling quota? No more tests needed... */ | 2057 | /* Journaling quota? */ |
2057 | if (!REISERFS_SB(sb)->s_qf_names[USRQUOTA] && | 2058 | if (REISERFS_SB(sb)->s_qf_names[type]) { |
2058 | !REISERFS_SB(sb)->s_qf_names[GRPQUOTA]) { | 2059 | /* Quotafile not of fs root? */ |
2059 | path_put(&nd.path); | 2060 | if (nd.path.dentry->d_parent->d_inode != sb->s_root->d_inode) |
2060 | return vfs_quota_on(sb, type, format_id, path, 0); | 2061 | reiserfs_warning(sb, |
2061 | } | ||
2062 | /* Quotafile not of fs root? */ | ||
2063 | if (nd.path.dentry->d_parent->d_inode != sb->s_root->d_inode) | ||
2064 | reiserfs_warning(sb, | ||
2065 | "reiserfs: Quota file not on filesystem root. " | 2062 | "reiserfs: Quota file not on filesystem root. " |
2066 | "Journalled quota will not work."); | 2063 | "Journalled quota will not work."); |
2064 | } | ||
2065 | |||
2066 | /* | ||
2067 | * When we journal data on quota file, we have to flush journal to see | ||
2068 | * all updates to the file when we bypass pagecache... | ||
2069 | */ | ||
2070 | if (reiserfs_file_data_log(inode)) { | ||
2071 | /* Just start temporary transaction and finish it */ | ||
2072 | err = journal_begin(&th, sb, 1); | ||
2073 | if (err) | ||
2074 | return err; | ||
2075 | err = journal_end_sync(&th, sb, 1); | ||
2076 | if (err) | ||
2077 | return err; | ||
2078 | } | ||
2067 | path_put(&nd.path); | 2079 | path_put(&nd.path); |
2068 | return vfs_quota_on(sb, type, format_id, path, 0); | 2080 | return vfs_quota_on(sb, type, format_id, path, 0); |
2069 | } | 2081 | } |