mirror of
https://github.com/torvalds/linux.git
synced 2024-11-10 22:21:40 +00:00
udf: Prevent write-unsupported filesystem to be remounted read-write
There are certain filesystem features which we support for reading but not for writing. We properly refuse to mount such filesystems read-write however for some features (such as read-only partitions), we don't check for these features when remounting the filesystem from read-only to read-write. Thus such filesystems could be remounted read-write leading to strange behavior (most likely crashes). Fix the problem by marking in superblock whether the filesystem has some features that are supported in read-only mode and check this flag during remount. Signed-off-by: Jan Kara <jack@suse.cz>
This commit is contained in:
parent
59fed3bf8a
commit
a9ad01bc75
@ -613,14 +613,11 @@ static int udf_remount_fs(struct super_block *sb, int *flags, char *options)
|
||||
struct udf_options uopt;
|
||||
struct udf_sb_info *sbi = UDF_SB(sb);
|
||||
int error = 0;
|
||||
struct logicalVolIntegrityDescImpUse *lvidiu = udf_sb_lvidiu(sb);
|
||||
|
||||
if (!(*flags & SB_RDONLY) && UDF_QUERY_FLAG(sb, UDF_FLAG_RW_INCOMPAT))
|
||||
return -EACCES;
|
||||
|
||||
sync_filesystem(sb);
|
||||
if (lvidiu) {
|
||||
int write_rev = le16_to_cpu(lvidiu->minUDFWriteRev);
|
||||
if (write_rev > UDF_MAX_WRITE_VERSION && !(*flags & SB_RDONLY))
|
||||
return -EACCES;
|
||||
}
|
||||
|
||||
uopt.flags = sbi->s_flags;
|
||||
uopt.uid = sbi->s_uid;
|
||||
@ -1257,6 +1254,7 @@ static int udf_load_partdesc(struct super_block *sb, sector_t block)
|
||||
ret = -EACCES;
|
||||
goto out_bh;
|
||||
}
|
||||
UDF_SET_FLAG(sb, UDF_FLAG_RW_INCOMPAT);
|
||||
ret = udf_load_vat(sb, i, type1_idx);
|
||||
if (ret < 0)
|
||||
goto out_bh;
|
||||
@ -2155,10 +2153,12 @@ static int udf_fill_super(struct super_block *sb, void *options, int silent)
|
||||
UDF_MAX_READ_VERSION);
|
||||
ret = -EINVAL;
|
||||
goto error_out;
|
||||
} else if (minUDFWriteRev > UDF_MAX_WRITE_VERSION &&
|
||||
!sb_rdonly(sb)) {
|
||||
ret = -EACCES;
|
||||
goto error_out;
|
||||
} else if (minUDFWriteRev > UDF_MAX_WRITE_VERSION) {
|
||||
if (!sb_rdonly(sb)) {
|
||||
ret = -EACCES;
|
||||
goto error_out;
|
||||
}
|
||||
UDF_SET_FLAG(sb, UDF_FLAG_RW_INCOMPAT);
|
||||
}
|
||||
|
||||
sbi->s_udfrev = minUDFWriteRev;
|
||||
@ -2176,10 +2176,12 @@ static int udf_fill_super(struct super_block *sb, void *options, int silent)
|
||||
}
|
||||
|
||||
if (sbi->s_partmaps[sbi->s_partition].s_partition_flags &
|
||||
UDF_PART_FLAG_READ_ONLY &&
|
||||
!sb_rdonly(sb)) {
|
||||
ret = -EACCES;
|
||||
goto error_out;
|
||||
UDF_PART_FLAG_READ_ONLY) {
|
||||
if (!sb_rdonly(sb)) {
|
||||
ret = -EACCES;
|
||||
goto error_out;
|
||||
}
|
||||
UDF_SET_FLAG(sb, UDF_FLAG_RW_INCOMPAT);
|
||||
}
|
||||
|
||||
if (udf_find_fileset(sb, &fileset, &rootdir)) {
|
||||
|
@ -30,6 +30,8 @@
|
||||
#define UDF_FLAG_LASTBLOCK_SET 16
|
||||
#define UDF_FLAG_BLOCKSIZE_SET 17
|
||||
#define UDF_FLAG_INCONSISTENT 18
|
||||
#define UDF_FLAG_RW_INCOMPAT 19 /* Set when we find RW incompatible
|
||||
* feature */
|
||||
|
||||
#define UDF_PART_FLAG_UNALLOC_BITMAP 0x0001
|
||||
#define UDF_PART_FLAG_UNALLOC_TABLE 0x0002
|
||||
|
Loading…
Reference in New Issue
Block a user