diff options
-rw-r--r-- | fs/ocfs2/ocfs2.h | 8 | ||||
-rw-r--r-- | fs/ocfs2/super.c | 82 |
2 files changed, 49 insertions, 41 deletions
diff --git a/fs/ocfs2/ocfs2.h b/fs/ocfs2/ocfs2.h index eae404602424..35ad46cf89b3 100644 --- a/fs/ocfs2/ocfs2.h +++ b/fs/ocfs2/ocfs2.h | |||
@@ -250,9 +250,11 @@ enum ocfs2_mount_options | |||
250 | OCFS2_MOUNT_LOCALFLOCKS = 1 << 5, /* No cluster aware user file locks */ | 250 | OCFS2_MOUNT_LOCALFLOCKS = 1 << 5, /* No cluster aware user file locks */ |
251 | OCFS2_MOUNT_NOUSERXATTR = 1 << 6, /* No user xattr */ | 251 | OCFS2_MOUNT_NOUSERXATTR = 1 << 6, /* No user xattr */ |
252 | OCFS2_MOUNT_INODE64 = 1 << 7, /* Allow inode numbers > 2^32 */ | 252 | OCFS2_MOUNT_INODE64 = 1 << 7, /* Allow inode numbers > 2^32 */ |
253 | OCFS2_MOUNT_POSIX_ACL = 1 << 8, /* POSIX access control lists */ | 253 | OCFS2_MOUNT_POSIX_ACL = 1 << 8, /* Force POSIX access control lists */ |
254 | OCFS2_MOUNT_USRQUOTA = 1 << 9, /* We support user quotas */ | 254 | OCFS2_MOUNT_NO_POSIX_ACL = 1 << 9, /* Disable POSIX access |
255 | OCFS2_MOUNT_GRPQUOTA = 1 << 10, /* We support group quotas */ | 255 | control lists */ |
256 | OCFS2_MOUNT_USRQUOTA = 1 << 10, /* We support user quotas */ | ||
257 | OCFS2_MOUNT_GRPQUOTA = 1 << 11, /* We support group quotas */ | ||
256 | }; | 258 | }; |
257 | 259 | ||
258 | #define OCFS2_OSB_SOFT_RO 0x0001 | 260 | #define OCFS2_OSB_SOFT_RO 0x0001 |
diff --git a/fs/ocfs2/super.c b/fs/ocfs2/super.c index da7d33a57cf6..a5116b9b7e70 100644 --- a/fs/ocfs2/super.c +++ b/fs/ocfs2/super.c | |||
@@ -100,6 +100,8 @@ struct mount_options | |||
100 | static int ocfs2_parse_options(struct super_block *sb, char *options, | 100 | static int ocfs2_parse_options(struct super_block *sb, char *options, |
101 | struct mount_options *mopt, | 101 | struct mount_options *mopt, |
102 | int is_remount); | 102 | int is_remount); |
103 | static int ocfs2_check_set_options(struct super_block *sb, | ||
104 | struct mount_options *options); | ||
103 | static int ocfs2_show_options(struct seq_file *s, struct vfsmount *mnt); | 105 | static int ocfs2_show_options(struct seq_file *s, struct vfsmount *mnt); |
104 | static void ocfs2_put_super(struct super_block *sb); | 106 | static void ocfs2_put_super(struct super_block *sb); |
105 | static int ocfs2_mount_volume(struct super_block *sb); | 107 | static int ocfs2_mount_volume(struct super_block *sb); |
@@ -600,7 +602,8 @@ static int ocfs2_remount(struct super_block *sb, int *flags, char *data) | |||
600 | 602 | ||
601 | lock_kernel(); | 603 | lock_kernel(); |
602 | 604 | ||
603 | if (!ocfs2_parse_options(sb, data, &parsed_options, 1)) { | 605 | if (!ocfs2_parse_options(sb, data, &parsed_options, 1) || |
606 | !ocfs2_check_set_options(sb, &parsed_options)) { | ||
604 | ret = -EINVAL; | 607 | ret = -EINVAL; |
605 | goto out; | 608 | goto out; |
606 | } | 609 | } |
@@ -691,8 +694,6 @@ unlock_osb: | |||
691 | if (!ret) { | 694 | if (!ret) { |
692 | /* Only save off the new mount options in case of a successful | 695 | /* Only save off the new mount options in case of a successful |
693 | * remount. */ | 696 | * remount. */ |
694 | if (!(osb->s_feature_incompat & OCFS2_FEATURE_INCOMPAT_XATTR)) | ||
695 | parsed_options.mount_opt &= ~OCFS2_MOUNT_POSIX_ACL; | ||
696 | osb->s_mount_opt = parsed_options.mount_opt; | 697 | osb->s_mount_opt = parsed_options.mount_opt; |
697 | osb->s_atime_quantum = parsed_options.atime_quantum; | 698 | osb->s_atime_quantum = parsed_options.atime_quantum; |
698 | osb->preferred_slot = parsed_options.slot; | 699 | osb->preferred_slot = parsed_options.slot; |
@@ -1011,31 +1012,16 @@ static int ocfs2_fill_super(struct super_block *sb, void *data, int silent) | |||
1011 | brelse(bh); | 1012 | brelse(bh); |
1012 | bh = NULL; | 1013 | bh = NULL; |
1013 | 1014 | ||
1014 | if (!(osb->s_feature_incompat & OCFS2_FEATURE_INCOMPAT_XATTR)) | 1015 | if (!ocfs2_check_set_options(sb, &parsed_options)) { |
1015 | parsed_options.mount_opt &= ~OCFS2_MOUNT_POSIX_ACL; | 1016 | status = -EINVAL; |
1016 | 1017 | goto read_super_error; | |
1018 | } | ||
1017 | osb->s_mount_opt = parsed_options.mount_opt; | 1019 | osb->s_mount_opt = parsed_options.mount_opt; |
1018 | osb->s_atime_quantum = parsed_options.atime_quantum; | 1020 | osb->s_atime_quantum = parsed_options.atime_quantum; |
1019 | osb->preferred_slot = parsed_options.slot; | 1021 | osb->preferred_slot = parsed_options.slot; |
1020 | osb->osb_commit_interval = parsed_options.commit_interval; | 1022 | osb->osb_commit_interval = parsed_options.commit_interval; |
1021 | osb->local_alloc_default_bits = ocfs2_megabytes_to_clusters(sb, parsed_options.localalloc_opt); | 1023 | osb->local_alloc_default_bits = ocfs2_megabytes_to_clusters(sb, parsed_options.localalloc_opt); |
1022 | osb->local_alloc_bits = osb->local_alloc_default_bits; | 1024 | osb->local_alloc_bits = osb->local_alloc_default_bits; |
1023 | if (osb->s_mount_opt & OCFS2_MOUNT_USRQUOTA && | ||
1024 | !OCFS2_HAS_RO_COMPAT_FEATURE(sb, | ||
1025 | OCFS2_FEATURE_RO_COMPAT_USRQUOTA)) { | ||
1026 | status = -EINVAL; | ||
1027 | mlog(ML_ERROR, "User quotas were requested, but this " | ||
1028 | "filesystem does not have the feature enabled.\n"); | ||
1029 | goto read_super_error; | ||
1030 | } | ||
1031 | if (osb->s_mount_opt & OCFS2_MOUNT_GRPQUOTA && | ||
1032 | !OCFS2_HAS_RO_COMPAT_FEATURE(sb, | ||
1033 | OCFS2_FEATURE_RO_COMPAT_GRPQUOTA)) { | ||
1034 | status = -EINVAL; | ||
1035 | mlog(ML_ERROR, "Group quotas were requested, but this " | ||
1036 | "filesystem does not have the feature enabled.\n"); | ||
1037 | goto read_super_error; | ||
1038 | } | ||
1039 | 1025 | ||
1040 | status = ocfs2_verify_userspace_stack(osb, &parsed_options); | 1026 | status = ocfs2_verify_userspace_stack(osb, &parsed_options); |
1041 | if (status) | 1027 | if (status) |
@@ -1245,6 +1231,40 @@ static struct file_system_type ocfs2_fs_type = { | |||
1245 | .next = NULL | 1231 | .next = NULL |
1246 | }; | 1232 | }; |
1247 | 1233 | ||
1234 | static int ocfs2_check_set_options(struct super_block *sb, | ||
1235 | struct mount_options *options) | ||
1236 | { | ||
1237 | if (options->mount_opt & OCFS2_MOUNT_USRQUOTA && | ||
1238 | !OCFS2_HAS_RO_COMPAT_FEATURE(sb, | ||
1239 | OCFS2_FEATURE_RO_COMPAT_USRQUOTA)) { | ||
1240 | mlog(ML_ERROR, "User quotas were requested, but this " | ||
1241 | "filesystem does not have the feature enabled.\n"); | ||
1242 | return 0; | ||
1243 | } | ||
1244 | if (options->mount_opt & OCFS2_MOUNT_GRPQUOTA && | ||
1245 | !OCFS2_HAS_RO_COMPAT_FEATURE(sb, | ||
1246 | OCFS2_FEATURE_RO_COMPAT_GRPQUOTA)) { | ||
1247 | mlog(ML_ERROR, "Group quotas were requested, but this " | ||
1248 | "filesystem does not have the feature enabled.\n"); | ||
1249 | return 0; | ||
1250 | } | ||
1251 | if (options->mount_opt & OCFS2_MOUNT_POSIX_ACL && | ||
1252 | !OCFS2_HAS_INCOMPAT_FEATURE(sb, OCFS2_FEATURE_INCOMPAT_XATTR)) { | ||
1253 | mlog(ML_ERROR, "ACL support requested but extended attributes " | ||
1254 | "feature is not enabled\n"); | ||
1255 | return 0; | ||
1256 | } | ||
1257 | /* No ACL setting specified? Use XATTR feature... */ | ||
1258 | if (!(options->mount_opt & (OCFS2_MOUNT_POSIX_ACL | | ||
1259 | OCFS2_MOUNT_NO_POSIX_ACL))) { | ||
1260 | if (OCFS2_HAS_INCOMPAT_FEATURE(sb, OCFS2_FEATURE_INCOMPAT_XATTR)) | ||
1261 | options->mount_opt |= OCFS2_MOUNT_POSIX_ACL; | ||
1262 | else | ||
1263 | options->mount_opt |= OCFS2_MOUNT_NO_POSIX_ACL; | ||
1264 | } | ||
1265 | return 1; | ||
1266 | } | ||
1267 | |||
1248 | static int ocfs2_parse_options(struct super_block *sb, | 1268 | static int ocfs2_parse_options(struct super_block *sb, |
1249 | char *options, | 1269 | char *options, |
1250 | struct mount_options *mopt, | 1270 | struct mount_options *mopt, |
@@ -1392,31 +1412,17 @@ static int ocfs2_parse_options(struct super_block *sb, | |||
1392 | mopt->mount_opt |= OCFS2_MOUNT_INODE64; | 1412 | mopt->mount_opt |= OCFS2_MOUNT_INODE64; |
1393 | break; | 1413 | break; |
1394 | case Opt_usrquota: | 1414 | case Opt_usrquota: |
1395 | /* We check only on remount, otherwise features | ||
1396 | * aren't yet initialized. */ | ||
1397 | if (is_remount && !OCFS2_HAS_RO_COMPAT_FEATURE(sb, | ||
1398 | OCFS2_FEATURE_RO_COMPAT_USRQUOTA)) { | ||
1399 | mlog(ML_ERROR, "User quota requested but " | ||
1400 | "filesystem feature is not set\n"); | ||
1401 | status = 0; | ||
1402 | goto bail; | ||
1403 | } | ||
1404 | mopt->mount_opt |= OCFS2_MOUNT_USRQUOTA; | 1415 | mopt->mount_opt |= OCFS2_MOUNT_USRQUOTA; |
1405 | break; | 1416 | break; |
1406 | case Opt_grpquota: | 1417 | case Opt_grpquota: |
1407 | if (is_remount && !OCFS2_HAS_RO_COMPAT_FEATURE(sb, | ||
1408 | OCFS2_FEATURE_RO_COMPAT_GRPQUOTA)) { | ||
1409 | mlog(ML_ERROR, "Group quota requested but " | ||
1410 | "filesystem feature is not set\n"); | ||
1411 | status = 0; | ||
1412 | goto bail; | ||
1413 | } | ||
1414 | mopt->mount_opt |= OCFS2_MOUNT_GRPQUOTA; | 1418 | mopt->mount_opt |= OCFS2_MOUNT_GRPQUOTA; |
1415 | break; | 1419 | break; |
1416 | case Opt_acl: | 1420 | case Opt_acl: |
1417 | mopt->mount_opt |= OCFS2_MOUNT_POSIX_ACL; | 1421 | mopt->mount_opt |= OCFS2_MOUNT_POSIX_ACL; |
1422 | mopt->mount_opt &= ~OCFS2_MOUNT_NO_POSIX_ACL; | ||
1418 | break; | 1423 | break; |
1419 | case Opt_noacl: | 1424 | case Opt_noacl: |
1425 | mopt->mount_opt |= OCFS2_MOUNT_NO_POSIX_ACL; | ||
1420 | mopt->mount_opt &= ~OCFS2_MOUNT_POSIX_ACL; | 1426 | mopt->mount_opt &= ~OCFS2_MOUNT_POSIX_ACL; |
1421 | break; | 1427 | break; |
1422 | default: | 1428 | default: |