summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--fs/ext4/ext4.h17
-rw-r--r--fs/ext4/super.c58
2 files changed, 64 insertions, 11 deletions
diff --git a/fs/ext4/ext4.h b/fs/ext4/ext4.h
index 48ae98819d35..f7257aa6bf81 100644
--- a/fs/ext4/ext4.h
+++ b/fs/ext4/ext4.h
@@ -239,8 +239,11 @@ struct ext4_io_submit {
239# define EXT4_BLOCK_SIZE(s) (EXT4_MIN_BLOCK_SIZE << (s)->s_log_block_size) 239# define EXT4_BLOCK_SIZE(s) (EXT4_MIN_BLOCK_SIZE << (s)->s_log_block_size)
240#endif 240#endif
241#define EXT4_ADDR_PER_BLOCK(s) (EXT4_BLOCK_SIZE(s) / sizeof(__u32)) 241#define EXT4_ADDR_PER_BLOCK(s) (EXT4_BLOCK_SIZE(s) / sizeof(__u32))
242#define EXT4_CLUSTER_SIZE(s) (EXT4_BLOCK_SIZE(s) << \
243 EXT4_SB(s)->s_cluster_bits)
242#ifdef __KERNEL__ 244#ifdef __KERNEL__
243# define EXT4_BLOCK_SIZE_BITS(s) ((s)->s_blocksize_bits) 245# define EXT4_BLOCK_SIZE_BITS(s) ((s)->s_blocksize_bits)
246# define EXT4_CLUSTER_BITS(s) (EXT4_SB(s)->s_cluster_bits)
244#else 247#else
245# define EXT4_BLOCK_SIZE_BITS(s) ((s)->s_log_block_size + 10) 248# define EXT4_BLOCK_SIZE_BITS(s) ((s)->s_log_block_size + 10)
246#endif 249#endif
@@ -306,6 +309,7 @@ struct flex_groups {
306#define EXT4_DESC_SIZE(s) (EXT4_SB(s)->s_desc_size) 309#define EXT4_DESC_SIZE(s) (EXT4_SB(s)->s_desc_size)
307#ifdef __KERNEL__ 310#ifdef __KERNEL__
308# define EXT4_BLOCKS_PER_GROUP(s) (EXT4_SB(s)->s_blocks_per_group) 311# define EXT4_BLOCKS_PER_GROUP(s) (EXT4_SB(s)->s_blocks_per_group)
312# define EXT4_CLUSTERS_PER_GROUP(s) (EXT4_SB(s)->s_clusters_per_group)
309# define EXT4_DESC_PER_BLOCK(s) (EXT4_SB(s)->s_desc_per_block) 313# define EXT4_DESC_PER_BLOCK(s) (EXT4_SB(s)->s_desc_per_block)
310# define EXT4_INODES_PER_GROUP(s) (EXT4_SB(s)->s_inodes_per_group) 314# define EXT4_INODES_PER_GROUP(s) (EXT4_SB(s)->s_inodes_per_group)
311# define EXT4_DESC_PER_BLOCK_BITS(s) (EXT4_SB(s)->s_desc_per_block_bits) 315# define EXT4_DESC_PER_BLOCK_BITS(s) (EXT4_SB(s)->s_desc_per_block_bits)
@@ -975,9 +979,9 @@ struct ext4_super_block {
975/*10*/ __le32 s_free_inodes_count; /* Free inodes count */ 979/*10*/ __le32 s_free_inodes_count; /* Free inodes count */
976 __le32 s_first_data_block; /* First Data Block */ 980 __le32 s_first_data_block; /* First Data Block */
977 __le32 s_log_block_size; /* Block size */ 981 __le32 s_log_block_size; /* Block size */
978 __le32 s_obso_log_frag_size; /* Obsoleted fragment size */ 982 __le32 s_log_cluster_size; /* Allocation cluster size */
979/*20*/ __le32 s_blocks_per_group; /* # Blocks per group */ 983/*20*/ __le32 s_blocks_per_group; /* # Blocks per group */
980 __le32 s_obso_frags_per_group; /* Obsoleted fragments per group */ 984 __le32 s_clusters_per_group; /* # Clusters per group */
981 __le32 s_inodes_per_group; /* # Inodes per group */ 985 __le32 s_inodes_per_group; /* # Inodes per group */
982 __le32 s_mtime; /* Mount time */ 986 __le32 s_mtime; /* Mount time */
983/*30*/ __le32 s_wtime; /* Write time */ 987/*30*/ __le32 s_wtime; /* Write time */
@@ -1073,7 +1077,10 @@ struct ext4_super_block {
1073 __u8 s_last_error_func[32]; /* function where the error happened */ 1077 __u8 s_last_error_func[32]; /* function where the error happened */
1074#define EXT4_S_ERR_END offsetof(struct ext4_super_block, s_mount_opts) 1078#define EXT4_S_ERR_END offsetof(struct ext4_super_block, s_mount_opts)
1075 __u8 s_mount_opts[64]; 1079 __u8 s_mount_opts[64];
1076 __le32 s_reserved[112]; /* Padding to the end of the block */ 1080 __le32 s_usr_quota_inum; /* inode for tracking user quota */
1081 __le32 s_grp_quota_inum; /* inode for tracking group quota */
1082 __le32 s_overhead_clusters; /* overhead blocks/clusters in fs */
1083 __le32 s_reserved[109]; /* Padding to the end of the block */
1077}; 1084};
1078 1085
1079#define EXT4_S_ERR_LEN (EXT4_S_ERR_END - EXT4_S_ERR_START) 1086#define EXT4_S_ERR_LEN (EXT4_S_ERR_END - EXT4_S_ERR_START)
@@ -1093,6 +1100,7 @@ struct ext4_sb_info {
1093 unsigned long s_desc_size; /* Size of a group descriptor in bytes */ 1100 unsigned long s_desc_size; /* Size of a group descriptor in bytes */
1094 unsigned long s_inodes_per_block;/* Number of inodes per block */ 1101 unsigned long s_inodes_per_block;/* Number of inodes per block */
1095 unsigned long s_blocks_per_group;/* Number of blocks in a group */ 1102 unsigned long s_blocks_per_group;/* Number of blocks in a group */
1103 unsigned long s_clusters_per_group; /* Number of clusters in a group */
1096 unsigned long s_inodes_per_group;/* Number of inodes in a group */ 1104 unsigned long s_inodes_per_group;/* Number of inodes in a group */
1097 unsigned long s_itb_per_group; /* Number of inode table blocks per group */ 1105 unsigned long s_itb_per_group; /* Number of inode table blocks per group */
1098 unsigned long s_gdb_count; /* Number of group descriptor blocks */ 1106 unsigned long s_gdb_count; /* Number of group descriptor blocks */
@@ -1101,6 +1109,8 @@ struct ext4_sb_info {
1101 ext4_group_t s_blockfile_groups;/* Groups acceptable for non-extent files */ 1109 ext4_group_t s_blockfile_groups;/* Groups acceptable for non-extent files */
1102 unsigned long s_overhead_last; /* Last calculated overhead */ 1110 unsigned long s_overhead_last; /* Last calculated overhead */
1103 unsigned long s_blocks_last; /* Last seen block count */ 1111 unsigned long s_blocks_last; /* Last seen block count */
1112 unsigned int s_cluster_ratio; /* Number of blocks per cluster */
1113 unsigned int s_cluster_bits; /* log2 of s_cluster_ratio */
1104 loff_t s_bitmap_maxbytes; /* max bytes for bitmap files */ 1114 loff_t s_bitmap_maxbytes; /* max bytes for bitmap files */
1105 struct buffer_head * s_sbh; /* Buffer containing the super block */ 1115 struct buffer_head * s_sbh; /* Buffer containing the super block */
1106 struct ext4_super_block *s_es; /* Pointer to the super block in the buffer */ 1116 struct ext4_super_block *s_es; /* Pointer to the super block in the buffer */
@@ -1367,6 +1377,7 @@ static inline void ext4_clear_state_flags(struct ext4_inode_info *ei)
1367#define EXT4_FEATURE_RO_COMPAT_DIR_NLINK 0x0020 1377#define EXT4_FEATURE_RO_COMPAT_DIR_NLINK 0x0020
1368#define EXT4_FEATURE_RO_COMPAT_EXTRA_ISIZE 0x0040 1378#define EXT4_FEATURE_RO_COMPAT_EXTRA_ISIZE 0x0040
1369#define EXT4_FEATURE_RO_COMPAT_QUOTA 0x0100 1379#define EXT4_FEATURE_RO_COMPAT_QUOTA 0x0100
1380#define EXT4_FEATURE_RO_COMPAT_BIGALLOC 0x0200
1370 1381
1371#define EXT4_FEATURE_INCOMPAT_COMPRESSION 0x0001 1382#define EXT4_FEATURE_INCOMPAT_COMPRESSION 0x0001
1372#define EXT4_FEATURE_INCOMPAT_FILETYPE 0x0002 1383#define EXT4_FEATURE_INCOMPAT_FILETYPE 0x0002
diff --git a/fs/ext4/super.c b/fs/ext4/super.c
index 5dcd0dacc591..823e7d9deee2 100644
--- a/fs/ext4/super.c
+++ b/fs/ext4/super.c
@@ -1953,7 +1953,7 @@ static int ext4_setup_super(struct super_block *sb, struct ext4_super_block *es,
1953 res = MS_RDONLY; 1953 res = MS_RDONLY;
1954 } 1954 }
1955 if (read_only) 1955 if (read_only)
1956 return res; 1956 goto done;
1957 if (!(sbi->s_mount_state & EXT4_VALID_FS)) 1957 if (!(sbi->s_mount_state & EXT4_VALID_FS))
1958 ext4_msg(sb, KERN_WARNING, "warning: mounting unchecked fs, " 1958 ext4_msg(sb, KERN_WARNING, "warning: mounting unchecked fs, "
1959 "running e2fsck is recommended"); 1959 "running e2fsck is recommended");
@@ -1984,6 +1984,7 @@ static int ext4_setup_super(struct super_block *sb, struct ext4_super_block *es,
1984 EXT4_SET_INCOMPAT_FEATURE(sb, EXT4_FEATURE_INCOMPAT_RECOVER); 1984 EXT4_SET_INCOMPAT_FEATURE(sb, EXT4_FEATURE_INCOMPAT_RECOVER);
1985 1985
1986 ext4_commit_super(sb, 1); 1986 ext4_commit_super(sb, 1);
1987done:
1987 if (test_opt(sb, DEBUG)) 1988 if (test_opt(sb, DEBUG))
1988 printk(KERN_INFO "[EXT4 FS bs=%lu, gc=%u, " 1989 printk(KERN_INFO "[EXT4 FS bs=%lu, gc=%u, "
1989 "bpg=%lu, ipg=%lu, mo=%04x, mo2=%04x]\n", 1990 "bpg=%lu, ipg=%lu, mo=%04x, mo2=%04x]\n",
@@ -3105,10 +3106,10 @@ static int ext4_fill_super(struct super_block *sb, void *data, int silent)
3105 char *cp; 3106 char *cp;
3106 const char *descr; 3107 const char *descr;
3107 int ret = -ENOMEM; 3108 int ret = -ENOMEM;
3108 int blocksize; 3109 int blocksize, clustersize;
3109 unsigned int db_count; 3110 unsigned int db_count;
3110 unsigned int i; 3111 unsigned int i;
3111 int needs_recovery, has_huge_files; 3112 int needs_recovery, has_huge_files, has_bigalloc;
3112 __u64 blocks_count; 3113 __u64 blocks_count;
3113 int err; 3114 int err;
3114 unsigned int journal_ioprio = DEFAULT_JOURNAL_IOPRIO; 3115 unsigned int journal_ioprio = DEFAULT_JOURNAL_IOPRIO;
@@ -3412,12 +3413,53 @@ static int ext4_fill_super(struct super_block *sb, void *data, int silent)
3412 sb->s_dirt = 1; 3413 sb->s_dirt = 1;
3413 } 3414 }
3414 3415
3415 if (sbi->s_blocks_per_group > blocksize * 8) { 3416 /* Handle clustersize */
3416 ext4_msg(sb, KERN_ERR, 3417 clustersize = BLOCK_SIZE << le32_to_cpu(es->s_log_cluster_size);
3417 "#blocks per group too big: %lu", 3418 has_bigalloc = EXT4_HAS_RO_COMPAT_FEATURE(sb,
3418 sbi->s_blocks_per_group); 3419 EXT4_FEATURE_RO_COMPAT_BIGALLOC);
3419 goto failed_mount; 3420 if (has_bigalloc) {
3421 if (clustersize < blocksize) {
3422 ext4_msg(sb, KERN_ERR,
3423 "cluster size (%d) smaller than "
3424 "block size (%d)", clustersize, blocksize);
3425 goto failed_mount;
3426 }
3427 sbi->s_cluster_bits = le32_to_cpu(es->s_log_cluster_size) -
3428 le32_to_cpu(es->s_log_block_size);
3429 sbi->s_clusters_per_group =
3430 le32_to_cpu(es->s_clusters_per_group);
3431 if (sbi->s_clusters_per_group > blocksize * 8) {
3432 ext4_msg(sb, KERN_ERR,
3433 "#clusters per group too big: %lu",
3434 sbi->s_clusters_per_group);
3435 goto failed_mount;
3436 }
3437 if (sbi->s_blocks_per_group !=
3438 (sbi->s_clusters_per_group * (clustersize / blocksize))) {
3439 ext4_msg(sb, KERN_ERR, "blocks per group (%lu) and "
3440 "clusters per group (%lu) inconsistent",
3441 sbi->s_blocks_per_group,
3442 sbi->s_clusters_per_group);
3443 goto failed_mount;
3444 }
3445 } else {
3446 if (clustersize != blocksize) {
3447 ext4_warning(sb, "fragment/cluster size (%d) != "
3448 "block size (%d)", clustersize,
3449 blocksize);
3450 clustersize = blocksize;
3451 }
3452 if (sbi->s_blocks_per_group > blocksize * 8) {
3453 ext4_msg(sb, KERN_ERR,
3454 "#blocks per group too big: %lu",
3455 sbi->s_blocks_per_group);
3456 goto failed_mount;
3457 }
3458 sbi->s_clusters_per_group = sbi->s_blocks_per_group;
3459 sbi->s_cluster_bits = 0;
3420 } 3460 }
3461 sbi->s_cluster_ratio = clustersize / blocksize;
3462
3421 if (sbi->s_inodes_per_group > blocksize * 8) { 3463 if (sbi->s_inodes_per_group > blocksize * 8) {
3422 ext4_msg(sb, KERN_ERR, 3464 ext4_msg(sb, KERN_ERR,
3423 "#inodes per group too big: %lu", 3465 "#inodes per group too big: %lu",