aboutsummaryrefslogtreecommitdiffstats
path: root/fs
diff options
context:
space:
mode:
authorChristoph Hellwig <hch@infradead.org>2010-05-19 07:16:40 -0400
committerJan Kara <jack@suse.cz>2010-05-24 08:06:39 -0400
commitc79d967de3741ceb60c5bbbf1b6f97eab9a89838 (patch)
tree5494e7b504cffb0ddc6942d1542c2b4a472207ed /fs
parenteea7feb072f5914ecafa95b3d83be0c229244d90 (diff)
quota: move remount handling into the filesystem
Currently do_remount_sb calls into the dquot code to tell it about going from rw to ro and ro to rw. Move this code into the filesystem to not depend on the dquot code in the VFS - note ocfs2 already ignores these calls and handles remount by itself. This gets rid of overloading the quotactl calls and allows to unify the VFS and XFS codepaths in that area later. Signed-off-by: Christoph Hellwig <hch@lst.de> Signed-off-by: Jan Kara <jack@suse.cz>
Diffstat (limited to 'fs')
-rw-r--r--fs/ext2/super.c13
-rw-r--r--fs/ext3/super.c11
-rw-r--r--fs/ext4/super.c10
-rw-r--r--fs/jfs/super.c10
-rw-r--r--fs/reiserfs/super.c8
-rw-r--r--fs/super.c9
-rw-r--r--fs/udf/super.c25
-rw-r--r--fs/ufs/super.c12
8 files changed, 84 insertions, 14 deletions
diff --git a/fs/ext2/super.c b/fs/ext2/super.c
index 71e9eb1fa696..73346de9af5c 100644
--- a/fs/ext2/super.c
+++ b/fs/ext2/super.c
@@ -1241,6 +1241,7 @@ static int ext2_remount (struct super_block * sb, int * flags, char * data)
1241 spin_unlock(&sbi->s_lock); 1241 spin_unlock(&sbi->s_lock);
1242 return 0; 1242 return 0;
1243 } 1243 }
1244
1244 /* 1245 /*
1245 * OK, we are remounting a valid rw partition rdonly, so set 1246 * OK, we are remounting a valid rw partition rdonly, so set
1246 * the rdonly flag and then mark the partition as valid again. 1247 * the rdonly flag and then mark the partition as valid again.
@@ -1248,6 +1249,14 @@ static int ext2_remount (struct super_block * sb, int * flags, char * data)
1248 es->s_state = cpu_to_le16(sbi->s_mount_state); 1249 es->s_state = cpu_to_le16(sbi->s_mount_state);
1249 es->s_mtime = cpu_to_le32(get_seconds()); 1250 es->s_mtime = cpu_to_le32(get_seconds());
1250 spin_unlock(&sbi->s_lock); 1251 spin_unlock(&sbi->s_lock);
1252
1253 err = vfs_dq_off(sb, 1);
1254 if (err < 0 && err != -ENOSYS) {
1255 err = -EBUSY;
1256 spin_lock(&sbi->s_lock);
1257 goto restore_opts;
1258 }
1259
1251 ext2_sync_super(sb, es, 1); 1260 ext2_sync_super(sb, es, 1);
1252 } else { 1261 } else {
1253 __le32 ret = EXT2_HAS_RO_COMPAT_FEATURE(sb, 1262 __le32 ret = EXT2_HAS_RO_COMPAT_FEATURE(sb,
@@ -1269,8 +1278,12 @@ static int ext2_remount (struct super_block * sb, int * flags, char * data)
1269 if (!ext2_setup_super (sb, es, 0)) 1278 if (!ext2_setup_super (sb, es, 0))
1270 sb->s_flags &= ~MS_RDONLY; 1279 sb->s_flags &= ~MS_RDONLY;
1271 spin_unlock(&sbi->s_lock); 1280 spin_unlock(&sbi->s_lock);
1281
1272 ext2_write_super(sb); 1282 ext2_write_super(sb);
1283
1284 vfs_dq_quota_on_remount(sb);
1273 } 1285 }
1286
1274 return 0; 1287 return 0;
1275restore_opts: 1288restore_opts:
1276 sbi->s_mount_opt = old_opts.s_mount_opt; 1289 sbi->s_mount_opt = old_opts.s_mount_opt;
diff --git a/fs/ext3/super.c b/fs/ext3/super.c
index 0fc1293d0e96..d0f8837b6255 100644
--- a/fs/ext3/super.c
+++ b/fs/ext3/super.c
@@ -2551,6 +2551,7 @@ static int ext3_remount (struct super_block * sb, int * flags, char * data)
2551 ext3_fsblk_t n_blocks_count = 0; 2551 ext3_fsblk_t n_blocks_count = 0;
2552 unsigned long old_sb_flags; 2552 unsigned long old_sb_flags;
2553 struct ext3_mount_options old_opts; 2553 struct ext3_mount_options old_opts;
2554 int enable_quota = 0;
2554 int err; 2555 int err;
2555#ifdef CONFIG_QUOTA 2556#ifdef CONFIG_QUOTA
2556 int i; 2557 int i;
@@ -2597,6 +2598,12 @@ static int ext3_remount (struct super_block * sb, int * flags, char * data)
2597 } 2598 }
2598 2599
2599 if (*flags & MS_RDONLY) { 2600 if (*flags & MS_RDONLY) {
2601 err = vfs_dq_off(sb, 1);
2602 if (err < 0 && err != -ENOSYS) {
2603 err = -EBUSY;
2604 goto restore_opts;
2605 }
2606
2600 /* 2607 /*
2601 * First of all, the unconditional stuff we have to do 2608 * First of all, the unconditional stuff we have to do
2602 * to disable replay of the journal when we next remount 2609 * to disable replay of the journal when we next remount
@@ -2651,6 +2658,7 @@ static int ext3_remount (struct super_block * sb, int * flags, char * data)
2651 goto restore_opts; 2658 goto restore_opts;
2652 if (!ext3_setup_super (sb, es, 0)) 2659 if (!ext3_setup_super (sb, es, 0))
2653 sb->s_flags &= ~MS_RDONLY; 2660 sb->s_flags &= ~MS_RDONLY;
2661 enable_quota = 1;
2654 } 2662 }
2655 } 2663 }
2656#ifdef CONFIG_QUOTA 2664#ifdef CONFIG_QUOTA
@@ -2662,6 +2670,9 @@ static int ext3_remount (struct super_block * sb, int * flags, char * data)
2662#endif 2670#endif
2663 unlock_super(sb); 2671 unlock_super(sb);
2664 unlock_kernel(); 2672 unlock_kernel();
2673
2674 if (enable_quota)
2675 vfs_dq_quota_on_remount(sb);
2665 return 0; 2676 return 0;
2666restore_opts: 2677restore_opts:
2667 sb->s_flags = old_sb_flags; 2678 sb->s_flags = old_sb_flags;
diff --git a/fs/ext4/super.c b/fs/ext4/super.c
index e14d22c170d5..fb1e191d0fa9 100644
--- a/fs/ext4/super.c
+++ b/fs/ext4/super.c
@@ -3574,6 +3574,7 @@ static int ext4_remount(struct super_block *sb, int *flags, char *data)
3574 ext4_fsblk_t n_blocks_count = 0; 3574 ext4_fsblk_t n_blocks_count = 0;
3575 unsigned long old_sb_flags; 3575 unsigned long old_sb_flags;
3576 struct ext4_mount_options old_opts; 3576 struct ext4_mount_options old_opts;
3577 int enable_quota = 0;
3577 ext4_group_t g; 3578 ext4_group_t g;
3578 unsigned int journal_ioprio = DEFAULT_JOURNAL_IOPRIO; 3579 unsigned int journal_ioprio = DEFAULT_JOURNAL_IOPRIO;
3579 int err; 3580 int err;
@@ -3630,6 +3631,12 @@ static int ext4_remount(struct super_block *sb, int *flags, char *data)
3630 } 3631 }
3631 3632
3632 if (*flags & MS_RDONLY) { 3633 if (*flags & MS_RDONLY) {
3634 err = vfs_dq_off(sb, 1);
3635 if (err < 0 && err != -ENOSYS) {
3636 err = -EBUSY;
3637 goto restore_opts;
3638 }
3639
3633 /* 3640 /*
3634 * First of all, the unconditional stuff we have to do 3641 * First of all, the unconditional stuff we have to do
3635 * to disable replay of the journal when we next remount 3642 * to disable replay of the journal when we next remount
@@ -3698,6 +3705,7 @@ static int ext4_remount(struct super_block *sb, int *flags, char *data)
3698 goto restore_opts; 3705 goto restore_opts;
3699 if (!ext4_setup_super(sb, es, 0)) 3706 if (!ext4_setup_super(sb, es, 0))
3700 sb->s_flags &= ~MS_RDONLY; 3707 sb->s_flags &= ~MS_RDONLY;
3708 enable_quota = 1;
3701 } 3709 }
3702 } 3710 }
3703 ext4_setup_system_zone(sb); 3711 ext4_setup_system_zone(sb);
@@ -3713,6 +3721,8 @@ static int ext4_remount(struct super_block *sb, int *flags, char *data)
3713#endif 3721#endif
3714 unlock_super(sb); 3722 unlock_super(sb);
3715 unlock_kernel(); 3723 unlock_kernel();
3724 if (enable_quota)
3725 vfs_dq_quota_on_remount(sb);
3716 return 0; 3726 return 0;
3717 3727
3718restore_opts: 3728restore_opts:
diff --git a/fs/jfs/super.c b/fs/jfs/super.c
index b66832ac33ac..5329d66a9704 100644
--- a/fs/jfs/super.c
+++ b/fs/jfs/super.c
@@ -396,10 +396,20 @@ static int jfs_remount(struct super_block *sb, int *flags, char *data)
396 396
397 JFS_SBI(sb)->flag = flag; 397 JFS_SBI(sb)->flag = flag;
398 ret = jfs_mount_rw(sb, 1); 398 ret = jfs_mount_rw(sb, 1);
399
400 /* mark the fs r/w for quota activity */
401 sb->s_flags &= ~MS_RDONLY;
402
399 unlock_kernel(); 403 unlock_kernel();
404 vfs_dq_quota_on_remount(sb);
400 return ret; 405 return ret;
401 } 406 }
402 if ((!(sb->s_flags & MS_RDONLY)) && (*flags & MS_RDONLY)) { 407 if ((!(sb->s_flags & MS_RDONLY)) && (*flags & MS_RDONLY)) {
408 rc = vfs_dq_off(sb, 1);
409 if (rc < 0 && rc != -ENOSYS) {
410 unlock_kernel();
411 return -EBUSY;
412 }
403 rc = jfs_umount_rw(sb); 413 rc = jfs_umount_rw(sb);
404 JFS_SBI(sb)->flag = flag; 414 JFS_SBI(sb)->flag = flag;
405 unlock_kernel(); 415 unlock_kernel();
diff --git a/fs/reiserfs/super.c b/fs/reiserfs/super.c
index 59125fb36d42..49a8ba02bc17 100644
--- a/fs/reiserfs/super.c
+++ b/fs/reiserfs/super.c
@@ -1242,6 +1242,13 @@ static int reiserfs_remount(struct super_block *s, int *mount_flags, char *arg)
1242 if (s->s_flags & MS_RDONLY) 1242 if (s->s_flags & MS_RDONLY)
1243 /* it is read-only already */ 1243 /* it is read-only already */
1244 goto out_ok; 1244 goto out_ok;
1245
1246 err = vfs_dq_off(s, 1);
1247 if (err < 0 && err != -ENOSYS) {
1248 err = -EBUSY;
1249 goto out_err;
1250 }
1251
1245 /* try to remount file system with read-only permissions */ 1252 /* try to remount file system with read-only permissions */
1246 if (sb_umount_state(rs) == REISERFS_VALID_FS 1253 if (sb_umount_state(rs) == REISERFS_VALID_FS
1247 || REISERFS_SB(s)->s_mount_state != REISERFS_VALID_FS) { 1254 || REISERFS_SB(s)->s_mount_state != REISERFS_VALID_FS) {
@@ -1295,6 +1302,7 @@ static int reiserfs_remount(struct super_block *s, int *mount_flags, char *arg)
1295 s->s_dirt = 0; 1302 s->s_dirt = 0;
1296 1303
1297 if (!(*mount_flags & MS_RDONLY)) { 1304 if (!(*mount_flags & MS_RDONLY)) {
1305 vfs_dq_quota_on_remount(s);
1298 finish_unfinished(s); 1306 finish_unfinished(s);
1299 reiserfs_xattr_init(s, *mount_flags); 1307 reiserfs_xattr_init(s, *mount_flags);
1300 } 1308 }
diff --git a/fs/super.c b/fs/super.c
index 69688b15f1fa..a38e6e9b6f69 100644
--- a/fs/super.c
+++ b/fs/super.c
@@ -524,7 +524,7 @@ rescan:
524int do_remount_sb(struct super_block *sb, int flags, void *data, int force) 524int do_remount_sb(struct super_block *sb, int flags, void *data, int force)
525{ 525{
526 int retval; 526 int retval;
527 int remount_rw, remount_ro; 527 int remount_ro;
528 528
529 if (sb->s_frozen != SB_UNFROZEN) 529 if (sb->s_frozen != SB_UNFROZEN)
530 return -EBUSY; 530 return -EBUSY;
@@ -540,7 +540,6 @@ int do_remount_sb(struct super_block *sb, int flags, void *data, int force)
540 sync_filesystem(sb); 540 sync_filesystem(sb);
541 541
542 remount_ro = (flags & MS_RDONLY) && !(sb->s_flags & MS_RDONLY); 542 remount_ro = (flags & MS_RDONLY) && !(sb->s_flags & MS_RDONLY);
543 remount_rw = !(flags & MS_RDONLY) && (sb->s_flags & MS_RDONLY);
544 543
545 /* If we are remounting RDONLY and current sb is read/write, 544 /* If we are remounting RDONLY and current sb is read/write,
546 make sure there are no rw files opened */ 545 make sure there are no rw files opened */
@@ -549,9 +548,6 @@ int do_remount_sb(struct super_block *sb, int flags, void *data, int force)
549 mark_files_ro(sb); 548 mark_files_ro(sb);
550 else if (!fs_may_remount_ro(sb)) 549 else if (!fs_may_remount_ro(sb))
551 return -EBUSY; 550 return -EBUSY;
552 retval = vfs_dq_off(sb, 1);
553 if (retval < 0 && retval != -ENOSYS)
554 return -EBUSY;
555 } 551 }
556 552
557 if (sb->s_op->remount_fs) { 553 if (sb->s_op->remount_fs) {
@@ -560,8 +556,7 @@ int do_remount_sb(struct super_block *sb, int flags, void *data, int force)
560 return retval; 556 return retval;
561 } 557 }
562 sb->s_flags = (sb->s_flags & ~MS_RMT_MASK) | (flags & MS_RMT_MASK); 558 sb->s_flags = (sb->s_flags & ~MS_RMT_MASK) | (flags & MS_RMT_MASK);
563 if (remount_rw) 559
564 vfs_dq_quota_on_remount(sb);
565 /* 560 /*
566 * Some filesystems modify their metadata via some other path than the 561 * Some filesystems modify their metadata via some other path than the
567 * bdev buffer cache (eg. use a private mapping, or directories in 562 * bdev buffer cache (eg. use a private mapping, or directories in
diff --git a/fs/udf/super.c b/fs/udf/super.c
index 1e4543cbcd27..9ab4e259404b 100644
--- a/fs/udf/super.c
+++ b/fs/udf/super.c
@@ -54,6 +54,7 @@
54#include <linux/vmalloc.h> 54#include <linux/vmalloc.h>
55#include <linux/errno.h> 55#include <linux/errno.h>
56#include <linux/mount.h> 56#include <linux/mount.h>
57#include <linux/quotaops.h>
57#include <linux/seq_file.h> 58#include <linux/seq_file.h>
58#include <linux/bitmap.h> 59#include <linux/bitmap.h>
59#include <linux/crc-itu-t.h> 60#include <linux/crc-itu-t.h>
@@ -557,6 +558,7 @@ static int udf_remount_fs(struct super_block *sb, int *flags, char *options)
557{ 558{
558 struct udf_options uopt; 559 struct udf_options uopt;
559 struct udf_sb_info *sbi = UDF_SB(sb); 560 struct udf_sb_info *sbi = UDF_SB(sb);
561 int error = 0;
560 562
561 uopt.flags = sbi->s_flags; 563 uopt.flags = sbi->s_flags;
562 uopt.uid = sbi->s_uid; 564 uopt.uid = sbi->s_uid;
@@ -582,17 +584,26 @@ static int udf_remount_fs(struct super_block *sb, int *flags, char *options)
582 *flags |= MS_RDONLY; 584 *flags |= MS_RDONLY;
583 } 585 }
584 586
585 if ((*flags & MS_RDONLY) == (sb->s_flags & MS_RDONLY)) { 587 if ((*flags & MS_RDONLY) == (sb->s_flags & MS_RDONLY))
586 unlock_kernel(); 588 goto out_unlock;
587 return 0; 589
588 } 590 if (*flags & MS_RDONLY) {
589 if (*flags & MS_RDONLY)
590 udf_close_lvid(sb); 591 udf_close_lvid(sb);
591 else 592
593 error = vfs_dq_off(sb, 1);
594 if (error < 0 && error != -ENOSYS)
595 error = -EBUSY;
596 } else {
592 udf_open_lvid(sb); 597 udf_open_lvid(sb);
593 598
599 /* mark the fs r/w for quota activity */
600 sb->s_flags &= ~MS_RDONLY;
601 vfs_dq_quota_on_remount(sb);
602 }
603
604out_unlock:
594 unlock_kernel(); 605 unlock_kernel();
595 return 0; 606 return error;
596} 607}
597 608
598/* Check Volume Structure Descriptors (ECMA 167 2/9.1) */ 609/* Check Volume Structure Descriptors (ECMA 167 2/9.1) */
diff --git a/fs/ufs/super.c b/fs/ufs/super.c
index 14743d935a93..be1f7b05bc28 100644
--- a/fs/ufs/super.c
+++ b/fs/ufs/super.c
@@ -1248,7 +1248,9 @@ static int ufs_remount (struct super_block *sb, int *mount_flags, char *data)
1248 struct ufs_super_block_first * usb1; 1248 struct ufs_super_block_first * usb1;
1249 struct ufs_super_block_third * usb3; 1249 struct ufs_super_block_third * usb3;
1250 unsigned new_mount_opt, ufstype; 1250 unsigned new_mount_opt, ufstype;
1251 int enable_quota = 0;
1251 unsigned flags; 1252 unsigned flags;
1253 int err;
1252 1254
1253 lock_kernel(); 1255 lock_kernel();
1254 lock_super(sb); 1256 lock_super(sb);
@@ -1289,6 +1291,13 @@ static int ufs_remount (struct super_block *sb, int *mount_flags, char *data)
1289 * fs was mouted as rw, remounting ro 1291 * fs was mouted as rw, remounting ro
1290 */ 1292 */
1291 if (*mount_flags & MS_RDONLY) { 1293 if (*mount_flags & MS_RDONLY) {
1294 err = vfs_dq_off(sb, 1);
1295 if (err < 0 && err != -ENOSYS) {
1296 unlock_super(sb);
1297 unlock_kernel();
1298 return -EBUSY;
1299 }
1300
1292 ufs_put_super_internal(sb); 1301 ufs_put_super_internal(sb);
1293 usb1->fs_time = cpu_to_fs32(sb, get_seconds()); 1302 usb1->fs_time = cpu_to_fs32(sb, get_seconds());
1294 if ((flags & UFS_ST_MASK) == UFS_ST_SUN 1303 if ((flags & UFS_ST_MASK) == UFS_ST_SUN
@@ -1327,11 +1336,14 @@ static int ufs_remount (struct super_block *sb, int *mount_flags, char *data)
1327 return -EPERM; 1336 return -EPERM;
1328 } 1337 }
1329 sb->s_flags &= ~MS_RDONLY; 1338 sb->s_flags &= ~MS_RDONLY;
1339 enable_quota = 1;
1330#endif 1340#endif
1331 } 1341 }
1332 UFS_SB(sb)->s_mount_opt = new_mount_opt; 1342 UFS_SB(sb)->s_mount_opt = new_mount_opt;
1333 unlock_super(sb); 1343 unlock_super(sb);
1334 unlock_kernel(); 1344 unlock_kernel();
1345 if (enable_quota)
1346 vfs_dq_quota_on_remount(sb);
1335 return 0; 1347 return 0;
1336} 1348}
1337 1349