Skip to content

Commit 5c2a430

Browse files
committed
Merge tag 'ext4-for_linus-6.15-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/tytso/ext4
Pull ext4 updates from Ted Ts'o: "Ext4 bug fixes and cleanups, including: - hardening against maliciously fuzzed file systems - backwards compatibility for the brief period when we attempted to ignore zero-width characters - avoid potentially BUG'ing if there is a file system corruption found during the file system unmount - fix free space reporting by statfs when project quotas are enabled and the free space is less than the remaining project quota Also improve performance when replaying a journal with a very large number of revoke records (applicable for Lustre volumes)" * tag 'ext4-for_linus-6.15-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/tytso/ext4: (71 commits) ext4: fix OOB read when checking dotdot dir ext4: on a remount, only log the ro or r/w state when it has changed ext4: correct the error handle in ext4_fallocate() ext4: Make sb update interval tunable ext4: avoid journaling sb update on error if journal is destroying ext4: define ext4_journal_destroy wrapper ext4: hash: simplify kzalloc(n * 1, ...) to kzalloc(n, ...) jbd2: add a missing data flush during file and fs synchronization ext4: don't over-report free space or inodes in statvfs ext4: clear DISCARD flag if device does not support discard jbd2: remove jbd2_journal_unfile_buffer() ext4: reorder capability check last ext4: update the comment about mb_optimize_scan jbd2: fix off-by-one while erasing journal ext4: remove references to bh->b_page ext4: goto right label 'out_mmap_sem' in ext4_setattr() ext4: fix out-of-bound read in ext4_xattr_inode_dec_ref_all() ext4: introduce ITAIL helper jbd2: remove redundant function jbd2_journal_has_csum_v2or3_feature ext4: remove redundant function ext4_has_metadata_csum ...
2 parents 4a4b30e + d5e2067 commit 5c2a430

35 files changed

+967
-1112
lines changed

Documentation/admin-guide/ext4.rst

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -238,11 +238,10 @@ When mounting an ext4 filesystem, the following option are accepted:
238238
configured using tune2fs)
239239

240240
data_err=ignore(*)
241-
Just print an error message if an error occurs in a file data buffer in
242-
ordered mode.
241+
Just print an error message if an error occurs in a file data buffer.
242+
243243
data_err=abort
244-
Abort the journal if an error occurs in a file data buffer in ordered
245-
mode.
244+
Abort the journal if an error occurs in a file data buffer.
246245

247246
grpid | bsdgroups
248247
New objects have the group ID of their parent.

Documentation/filesystems/journalling.rst

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -111,9 +111,7 @@ a callback function when the transaction is finally committed to disk,
111111
so that you can do some of your own management. You ask the journalling
112112
layer for calling the callback by simply setting
113113
``journal->j_commit_callback`` function pointer and that function is
114-
called after each transaction commit. You can also use
115-
``transaction->t_private_list`` for attaching entries to a transaction
116-
that need processing when the transaction commits.
114+
called after each transaction commit.
117115

118116
JBD2 also provides a way to block all transaction updates via
119117
jbd2_journal_lock_updates() /

fs/ext4/balloc.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -649,8 +649,8 @@ static int ext4_has_free_clusters(struct ext4_sb_info *sbi,
649649
/* Hm, nope. Are (enough) root reserved clusters available? */
650650
if (uid_eq(sbi->s_resuid, current_fsuid()) ||
651651
(!gid_eq(sbi->s_resgid, GLOBAL_ROOT_GID) && in_group_p(sbi->s_resgid)) ||
652-
capable(CAP_SYS_RESOURCE) ||
653-
(flags & EXT4_MB_USE_ROOT_BLOCKS)) {
652+
(flags & EXT4_MB_USE_ROOT_BLOCKS) ||
653+
capable(CAP_SYS_RESOURCE)) {
654654

655655
if (free_clusters >= (nclusters + dirty_clusters +
656656
resv_clusters))

fs/ext4/bitmap.c

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ int ext4_inode_bitmap_csum_verify(struct super_block *sb,
2525
struct ext4_sb_info *sbi = EXT4_SB(sb);
2626
int sz;
2727

28-
if (!ext4_has_metadata_csum(sb))
28+
if (!ext4_has_feature_metadata_csum(sb))
2929
return 1;
3030

3131
sz = EXT4_INODES_PER_GROUP(sb) >> 3;
@@ -48,7 +48,7 @@ void ext4_inode_bitmap_csum_set(struct super_block *sb,
4848
struct ext4_sb_info *sbi = EXT4_SB(sb);
4949
int sz;
5050

51-
if (!ext4_has_metadata_csum(sb))
51+
if (!ext4_has_feature_metadata_csum(sb))
5252
return;
5353

5454
sz = EXT4_INODES_PER_GROUP(sb) >> 3;
@@ -67,7 +67,7 @@ int ext4_block_bitmap_csum_verify(struct super_block *sb,
6767
struct ext4_sb_info *sbi = EXT4_SB(sb);
6868
int sz = EXT4_CLUSTERS_PER_GROUP(sb) / 8;
6969

70-
if (!ext4_has_metadata_csum(sb))
70+
if (!ext4_has_feature_metadata_csum(sb))
7171
return 1;
7272

7373
provided = le16_to_cpu(gdp->bg_block_bitmap_csum_lo);
@@ -89,7 +89,7 @@ void ext4_block_bitmap_csum_set(struct super_block *sb,
8989
__u32 csum;
9090
struct ext4_sb_info *sbi = EXT4_SB(sb);
9191

92-
if (!ext4_has_metadata_csum(sb))
92+
if (!ext4_has_feature_metadata_csum(sb))
9393
return;
9494

9595
csum = ext4_chksum(sbi, sbi->s_csum_seed, (__u8 *)bh->b_data, sz);

fs/ext4/dir.c

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -86,7 +86,7 @@ int __ext4_check_dir_entry(const char *function, unsigned int line,
8686
dir->i_sb->s_blocksize);
8787
const int next_offset = ((char *) de - buf) + rlen;
8888
bool fake = is_fake_dir_entry(de);
89-
bool has_csum = ext4_has_metadata_csum(dir->i_sb);
89+
bool has_csum = ext4_has_feature_metadata_csum(dir->i_sb);
9090

9191
if (unlikely(rlen < ext4_dir_rec_len(1, fake ? NULL : dir)))
9292
error_msg = "rec_len is smaller than minimal";
@@ -104,6 +104,9 @@ int __ext4_check_dir_entry(const char *function, unsigned int line,
104104
else if (unlikely(le32_to_cpu(de->inode) >
105105
le32_to_cpu(EXT4_SB(dir->i_sb)->s_es->s_inodes_count)))
106106
error_msg = "inode out of bounds";
107+
else if (unlikely(next_offset == size && de->name_len == 1 &&
108+
de->name[0] == '.'))
109+
error_msg = "'.' directory cannot be the last in data block";
107110
else
108111
return 0;
109112

@@ -145,7 +148,7 @@ static int ext4_readdir(struct file *file, struct dir_context *ctx)
145148
return err;
146149

147150
/* Can we just clear INDEX flag to ignore htree information? */
148-
if (!ext4_has_metadata_csum(sb)) {
151+
if (!ext4_has_feature_metadata_csum(sb)) {
149152
/*
150153
* We don't set the inode dirty flag since it's not
151154
* critical that it gets flushed back to the disk.

fs/ext4/ext4.h

Lines changed: 53 additions & 41 deletions
Original file line numberDiff line numberDiff line change
@@ -278,7 +278,10 @@ struct ext4_system_blocks {
278278
/*
279279
* Flags for ext4_io_end->flags
280280
*/
281-
#define EXT4_IO_END_UNWRITTEN 0x0001
281+
#define EXT4_IO_END_UNWRITTEN 0x0001
282+
#define EXT4_IO_END_FAILED 0x0002
283+
284+
#define EXT4_IO_END_DEFER_COMPLETION (EXT4_IO_END_UNWRITTEN | EXT4_IO_END_FAILED)
282285

283286
struct ext4_io_end_vec {
284287
struct list_head list; /* list of io_end_vec */
@@ -367,6 +370,8 @@ struct ext4_io_submit {
367370
#define EXT4_MAX_BLOCKS(size, offset, blkbits) \
368371
((EXT4_BLOCK_ALIGN(size + offset, blkbits) >> blkbits) - (offset >> \
369372
blkbits))
373+
#define EXT4_B_TO_LBLK(inode, offset) \
374+
(round_up((offset), i_blocksize(inode)) >> (inode)->i_blkbits)
370375

371376
/* Translate a block number to a cluster number */
372377
#define EXT4_B2C(sbi, blk) ((blk) >> (sbi)->s_cluster_bits)
@@ -1058,7 +1063,8 @@ struct ext4_inode_info {
10581063

10591064
/* Number of ongoing updates on this inode */
10601065
atomic_t i_fc_updates;
1061-
atomic_t i_unwritten; /* Nr. of inflight conversions pending */
1066+
1067+
spinlock_t i_raw_lock; /* protects updates to the raw inode */
10621068

10631069
/* Fast commit wait queue for this inode */
10641070
wait_queue_head_t i_fc_wait;
@@ -1097,8 +1103,6 @@ struct ext4_inode_info {
10971103
struct inode vfs_inode;
10981104
struct jbd2_inode *jinode;
10991105

1100-
spinlock_t i_raw_lock; /* protects updates to the raw inode */
1101-
11021106
/*
11031107
* File creation time. Its function is same as that of
11041108
* struct timespec64 i_{a,c,m}time in the generic inode.
@@ -1141,6 +1145,7 @@ struct ext4_inode_info {
11411145
/* quota space reservation, managed internally by quota code */
11421146
qsize_t i_reserved_quota;
11431147
#endif
1148+
spinlock_t i_block_reservation_lock;
11441149

11451150
/* Lock protecting lists below */
11461151
spinlock_t i_completed_io_lock;
@@ -1151,8 +1156,6 @@ struct ext4_inode_info {
11511156
struct list_head i_rsv_conversion_list;
11521157
struct work_struct i_rsv_conversion_work;
11531158

1154-
spinlock_t i_block_reservation_lock;
1155-
11561159
/*
11571160
* Transactions that contain inode's metadata needed to complete
11581161
* fsync and fdatasync, respectively.
@@ -1606,6 +1609,8 @@ struct ext4_sb_info {
16061609
unsigned int s_mb_prefetch;
16071610
unsigned int s_mb_prefetch_limit;
16081611
unsigned int s_mb_best_avail_max_trim_order;
1612+
unsigned int s_sb_update_sec;
1613+
unsigned int s_sb_update_kb;
16091614

16101615
/* stats for buddy allocator */
16111616
atomic_t s_bal_reqs; /* number of reqs with len > 1 */
@@ -1821,7 +1826,8 @@ static inline int ext4_valid_inum(struct super_block *sb, unsigned long ino)
18211826
*/
18221827
enum {
18231828
EXT4_MF_MNTDIR_SAMPLED,
1824-
EXT4_MF_FC_INELIGIBLE /* Fast commit ineligible */
1829+
EXT4_MF_FC_INELIGIBLE, /* Fast commit ineligible */
1830+
EXT4_MF_JOURNAL_DESTROY /* Journal is in process of destroying */
18251831
};
18261832

18271833
static inline void ext4_set_mount_flag(struct super_block *sb, int bit)
@@ -2232,15 +2238,32 @@ extern int ext4_feature_set_ok(struct super_block *sb, int readonly);
22322238
/*
22332239
* Superblock flags
22342240
*/
2235-
#define EXT4_FLAGS_RESIZING 0
2236-
#define EXT4_FLAGS_SHUTDOWN 1
2237-
#define EXT4_FLAGS_BDEV_IS_DAX 2
2241+
enum {
2242+
EXT4_FLAGS_RESIZING, /* Avoid superblock update and resize race */
2243+
EXT4_FLAGS_SHUTDOWN, /* Prevent access to the file system */
2244+
EXT4_FLAGS_BDEV_IS_DAX, /* Current block device support DAX */
2245+
EXT4_FLAGS_EMERGENCY_RO,/* Emergency read-only due to fs errors */
2246+
};
22382247

22392248
static inline int ext4_forced_shutdown(struct super_block *sb)
22402249
{
22412250
return test_bit(EXT4_FLAGS_SHUTDOWN, &EXT4_SB(sb)->s_ext4_flags);
22422251
}
22432252

2253+
static inline int ext4_emergency_ro(struct super_block *sb)
2254+
{
2255+
return test_bit(EXT4_FLAGS_EMERGENCY_RO, &EXT4_SB(sb)->s_ext4_flags);
2256+
}
2257+
2258+
static inline int ext4_emergency_state(struct super_block *sb)
2259+
{
2260+
if (unlikely(ext4_forced_shutdown(sb)))
2261+
return -EIO;
2262+
if (unlikely(ext4_emergency_ro(sb)))
2263+
return -EROFS;
2264+
return 0;
2265+
}
2266+
22442267
/*
22452268
* Default values for user and/or group using reserved blocks
22462269
*/
@@ -2277,6 +2300,13 @@ static inline int ext4_forced_shutdown(struct super_block *sb)
22772300
#define EXT4_DEF_MIN_BATCH_TIME 0
22782301
#define EXT4_DEF_MAX_BATCH_TIME 15000 /* 15ms */
22792302

2303+
/*
2304+
* Default values for superblock update
2305+
*/
2306+
#define EXT4_DEF_SB_UPDATE_INTERVAL_SEC (3600) /* seconds (1 hour) */
2307+
#define EXT4_DEF_SB_UPDATE_INTERVAL_KB (16384) /* kilobytes (16MB) */
2308+
2309+
22802310
/*
22812311
* Minimum number of groups in a flexgroup before we separate out
22822312
* directories into the first block group of a flexgroup
@@ -2810,8 +2840,7 @@ extern int ext4_htree_store_dirent(struct file *dir_file, __u32 hash,
28102840
struct ext4_dir_entry_2 *dirent,
28112841
struct fscrypt_str *ent_name);
28122842
extern void ext4_htree_free_dir_info(struct dir_private_info *p);
2813-
extern int ext4_find_dest_de(struct inode *dir, struct inode *inode,
2814-
struct buffer_head *bh,
2843+
extern int ext4_find_dest_de(struct inode *dir, struct buffer_head *bh,
28152844
void *buf, int buf_size,
28162845
struct ext4_filename *fname,
28172846
struct ext4_dir_entry_2 **dest_de);
@@ -3001,6 +3030,8 @@ extern int ext4_inode_attach_jinode(struct inode *inode);
30013030
extern int ext4_can_truncate(struct inode *inode);
30023031
extern int ext4_truncate(struct inode *);
30033032
extern int ext4_break_layouts(struct inode *);
3033+
extern int ext4_truncate_page_cache_block_range(struct inode *inode,
3034+
loff_t start, loff_t end);
30043035
extern int ext4_punch_hole(struct file *file, loff_t offset, loff_t length);
30053036
extern void ext4_set_inode_flags(struct inode *, bool init);
30063037
extern int ext4_alloc_da_blocks(struct inode *inode);
@@ -3259,14 +3290,10 @@ extern void ext4_group_desc_csum_set(struct super_block *sb, __u32 group,
32593290
extern int ext4_register_li_request(struct super_block *sb,
32603291
ext4_group_t first_not_zeroed);
32613292

3262-
static inline int ext4_has_metadata_csum(struct super_block *sb)
3263-
{
3264-
return ext4_has_feature_metadata_csum(sb);
3265-
}
3266-
32673293
static inline int ext4_has_group_desc_csum(struct super_block *sb)
32683294
{
3269-
return ext4_has_feature_gdt_csum(sb) || ext4_has_metadata_csum(sb);
3295+
return ext4_has_feature_gdt_csum(sb) ||
3296+
ext4_has_feature_metadata_csum(sb);
32703297
}
32713298

32723299
#define ext4_read_incompat_64bit_val(es, name) \
@@ -3546,11 +3573,11 @@ extern int ext4_try_to_write_inline_data(struct address_space *mapping,
35463573
struct folio **foliop);
35473574
int ext4_write_inline_data_end(struct inode *inode, loff_t pos, unsigned len,
35483575
unsigned copied, struct folio *folio);
3549-
extern int ext4_da_write_inline_data_begin(struct address_space *mapping,
3550-
struct inode *inode,
3551-
loff_t pos, unsigned len,
3552-
struct folio **foliop,
3553-
void **fsdata);
3576+
extern int ext4_generic_write_inline_data(struct address_space *mapping,
3577+
struct inode *inode,
3578+
loff_t pos, unsigned len,
3579+
struct folio **foliop,
3580+
void **fsdata, bool da);
35543581
extern int ext4_try_add_inline_entry(handle_t *handle,
35553582
struct ext4_filename *fname,
35563583
struct inode *dir, struct inode *inode);
@@ -3785,34 +3812,19 @@ static inline void set_bitmap_uptodate(struct buffer_head *bh)
37853812
set_bit(BH_BITMAP_UPTODATE, &(bh)->b_state);
37863813
}
37873814

3788-
/* For ioend & aio unwritten conversion wait queues */
3789-
#define EXT4_WQ_HASH_SZ 37
3790-
#define ext4_ioend_wq(v) (&ext4__ioend_wq[((unsigned long)(v)) %\
3791-
EXT4_WQ_HASH_SZ])
3792-
extern wait_queue_head_t ext4__ioend_wq[EXT4_WQ_HASH_SZ];
3793-
37943815
extern int ext4_resize_begin(struct super_block *sb);
37953816
extern int ext4_resize_end(struct super_block *sb, bool update_backups);
37963817

3797-
static inline void ext4_set_io_unwritten_flag(struct inode *inode,
3798-
struct ext4_io_end *io_end)
3818+
static inline void ext4_set_io_unwritten_flag(struct ext4_io_end *io_end)
37993819
{
3800-
if (!(io_end->flag & EXT4_IO_END_UNWRITTEN)) {
3820+
if (!(io_end->flag & EXT4_IO_END_UNWRITTEN))
38013821
io_end->flag |= EXT4_IO_END_UNWRITTEN;
3802-
atomic_inc(&EXT4_I(inode)->i_unwritten);
3803-
}
38043822
}
38053823

38063824
static inline void ext4_clear_io_unwritten_flag(ext4_io_end_t *io_end)
38073825
{
3808-
struct inode *inode = io_end->inode;
3809-
3810-
if (io_end->flag & EXT4_IO_END_UNWRITTEN) {
3826+
if (io_end->flag & EXT4_IO_END_UNWRITTEN)
38113827
io_end->flag &= ~EXT4_IO_END_UNWRITTEN;
3812-
/* Wake up anyone waiting on unwritten extent conversion */
3813-
if (atomic_dec_and_test(&EXT4_I(inode)->i_unwritten))
3814-
wake_up_all(ext4_ioend_wq(inode));
3815-
}
38163828
}
38173829

38183830
extern const struct iomap_ops ext4_iomap_ops;

fs/ext4/ext4_jbd2.c

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -63,12 +63,14 @@ static void ext4_put_nojournal(handle_t *handle)
6363
*/
6464
static int ext4_journal_check_start(struct super_block *sb)
6565
{
66+
int ret;
6667
journal_t *journal;
6768

6869
might_sleep();
6970

70-
if (unlikely(ext4_forced_shutdown(sb)))
71-
return -EIO;
71+
ret = ext4_emergency_state(sb);
72+
if (unlikely(ret))
73+
return ret;
7274

7375
if (WARN_ON_ONCE(sb_rdonly(sb)))
7476
return -EROFS;
@@ -244,7 +246,8 @@ int __ext4_journal_get_write_access(const char *where, unsigned int line,
244246
}
245247
} else
246248
ext4_check_bdev_write_error(sb);
247-
if (trigger_type == EXT4_JTR_NONE || !ext4_has_metadata_csum(sb))
249+
if (trigger_type == EXT4_JTR_NONE ||
250+
!ext4_has_feature_metadata_csum(sb))
248251
return 0;
249252
BUG_ON(trigger_type >= EXT4_JOURNAL_TRIGGER_COUNT);
250253
jbd2_journal_set_triggers(bh,
@@ -331,7 +334,8 @@ int __ext4_journal_get_create_access(const char *where, unsigned int line,
331334
err);
332335
return err;
333336
}
334-
if (trigger_type == EXT4_JTR_NONE || !ext4_has_metadata_csum(sb))
337+
if (trigger_type == EXT4_JTR_NONE ||
338+
!ext4_has_feature_metadata_csum(sb))
335339
return 0;
336340
BUG_ON(trigger_type >= EXT4_JOURNAL_TRIGGER_COUNT);
337341
jbd2_journal_set_triggers(bh,

0 commit comments

Comments
 (0)