mirror of
https://github.com/BobTheBlinker/android_kernel_motorola_sm6375.git
synced 2026-10-29 11:11:45 -04:00
Merge branch 'android11-5.4' into branch 'android11-5.4-lts'
Sync up with android11-5.4 for the following commits:7e6cbbe7e5Merge tag 'android11-5.4.210_r00' into android11-5.4297aa83408ANDROID: incfs: Add check for ATTR_KILL_SUID and ATTR_MODE in incfs_setattr26eb689452BACKPORT: f2fs: do not set compression bit if kernel doesn't support17bdd623f3UPSTREAM: f2fs: fix UAF in f2fs_available_free_memory7e4f972231ANDROID: f2fs: check nr_pages for readaheadf711e743ecUPSTREAM: f2fs: guarantee to write dirty data when enabling checkpoint backd7b2931cceFROMGIT: f2fs: flush data when enabling checkpoint back601b2ed3e6BACKPORT: f2fs: introduce FI_COMPRESS_RELEASED instead of using IMMUTABLE bitd2972f90d6BACKPORT: f2fs: enforce the immutable flag on open filesd2e72fa0b9BACKPORT: f2fs: change i_compr_blocks of inode to atomic value8629059128BACKPORT: f2fs: make file immutable even if releasing zero compression block3cf0f8245dBACKPORT: f2fs: compress: remove unneeded preallocation012ab662e2ANDROID: binder: fix pending prio state for early exitda97a10882ANDROID: binder: fix race in priority restore308230b9d7ANDROID: binder: switch task argument for binder_thread807b6742c9ANDROID: binder: pass desired priority by reference88c3fd6461ANDROID: binder: fold common setup of node_priofffb2b5badBACKPORT: Bluetooth: L2CAP: Fix use-after-free caused by l2cap_chan_put458b37a82dFROMLIST: binder: fix UAF of ref->proc caused by race condition Signed-off-by: Greg Kroah-Hartman <[email protected]> Change-Id: Ib2da4c15fc4b6ad84bc36ba9b2f8b3d0a2f84e0a
This commit is contained in:
commit
366e92d405
10 changed files with 206 additions and 102 deletions
|
|
@ -809,6 +809,10 @@ static int __f2fs_cluster_blocks(struct compress_ctx *cc, bool compr)
|
|||
ret++;
|
||||
}
|
||||
}
|
||||
|
||||
f2fs_bug_on(F2FS_I_SB(inode),
|
||||
!compr && ret != cc->cluster_size &&
|
||||
!is_inode_flag_set(cc->inode, FI_COMPRESS_RELEASED));
|
||||
}
|
||||
fail:
|
||||
f2fs_put_dnode(&dn);
|
||||
|
|
@ -879,21 +883,16 @@ static int prepare_compress_overwrite(struct compress_ctx *cc,
|
|||
struct f2fs_sb_info *sbi = F2FS_I_SB(cc->inode);
|
||||
struct address_space *mapping = cc->inode->i_mapping;
|
||||
struct page *page;
|
||||
struct dnode_of_data dn;
|
||||
sector_t last_block_in_bio;
|
||||
unsigned fgp_flag = FGP_LOCK | FGP_WRITE | FGP_CREAT;
|
||||
pgoff_t start_idx = start_idx_of_cluster(cc);
|
||||
int i, ret;
|
||||
bool prealloc;
|
||||
|
||||
retry:
|
||||
ret = f2fs_cluster_blocks(cc, false);
|
||||
if (ret <= 0)
|
||||
return ret;
|
||||
|
||||
/* compressed case */
|
||||
prealloc = (ret < cc->cluster_size);
|
||||
|
||||
ret = f2fs_init_compress_ctx(cc);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
|
@ -949,25 +948,6 @@ retry:
|
|||
}
|
||||
}
|
||||
|
||||
if (prealloc) {
|
||||
__do_map_lock(sbi, F2FS_GET_BLOCK_PRE_AIO, true);
|
||||
|
||||
set_new_dnode(&dn, cc->inode, NULL, NULL, 0);
|
||||
|
||||
for (i = cc->cluster_size - 1; i > 0; i--) {
|
||||
ret = f2fs_get_block(&dn, start_idx + i);
|
||||
if (ret) {
|
||||
i = cc->cluster_size;
|
||||
break;
|
||||
}
|
||||
|
||||
if (dn.data_blkaddr != NEW_ADDR)
|
||||
break;
|
||||
}
|
||||
|
||||
__do_map_lock(sbi, F2FS_GET_BLOCK_PRE_AIO, false);
|
||||
}
|
||||
|
||||
if (likely(!ret)) {
|
||||
*fsdata = cc->rpages;
|
||||
*pagep = cc->rpages[offset_in_cluster(cc, index)];
|
||||
|
|
|
|||
|
|
@ -2359,6 +2359,10 @@ int f2fs_mpage_readpages(struct address_space *mapping,
|
|||
unsigned max_nr_pages = nr_pages;
|
||||
int ret = 0;
|
||||
|
||||
/* this is real from f2fs_merkle_tree_readahead() in old kernel only. */
|
||||
if (!nr_pages)
|
||||
return 0;
|
||||
|
||||
map.m_pblk = 0;
|
||||
map.m_lblk = 0;
|
||||
map.m_len = 0;
|
||||
|
|
|
|||
|
|
@ -762,6 +762,7 @@ enum {
|
|||
FI_VERITY_IN_PROGRESS, /* building fs-verity Merkle tree */
|
||||
FI_COMPRESSED_FILE, /* indicate file's data can be compressed */
|
||||
FI_MMAP_FILE, /* indicate file was mmapped */
|
||||
FI_COMPRESS_RELEASED, /* compressed blocks were released */
|
||||
FI_MAX, /* max flag, never be used */
|
||||
};
|
||||
|
||||
|
|
@ -814,7 +815,7 @@ struct f2fs_inode_info {
|
|||
struct timespec64 i_disk_time[4];/* inode disk times */
|
||||
|
||||
/* for file compress */
|
||||
u64 i_compr_blocks; /* # of compressed blocks */
|
||||
atomic_t i_compr_blocks; /* # of compressed blocks */
|
||||
unsigned char i_compress_algorithm; /* algorithm type */
|
||||
unsigned char i_log_cluster_size; /* log of cluster size */
|
||||
unsigned int i_cluster_size; /* cluster size */
|
||||
|
|
@ -2669,6 +2670,7 @@ static inline void __mark_inode_dirty_flag(struct inode *inode,
|
|||
case FI_DATA_EXIST:
|
||||
case FI_INLINE_DOTS:
|
||||
case FI_PIN_FILE:
|
||||
case FI_COMPRESS_RELEASED:
|
||||
f2fs_mark_inode_dirty_sync(inode, true);
|
||||
}
|
||||
}
|
||||
|
|
@ -2790,6 +2792,8 @@ static inline void get_inline_info(struct inode *inode, struct f2fs_inode *ri)
|
|||
set_bit(FI_EXTRA_ATTR, fi->flags);
|
||||
if (ri->i_inline & F2FS_PIN_FILE)
|
||||
set_bit(FI_PIN_FILE, fi->flags);
|
||||
if (ri->i_inline & F2FS_COMPRESS_RELEASED)
|
||||
set_bit(FI_COMPRESS_RELEASED, fi->flags);
|
||||
}
|
||||
|
||||
static inline void set_raw_inline(struct inode *inode, struct f2fs_inode *ri)
|
||||
|
|
@ -2810,6 +2814,8 @@ static inline void set_raw_inline(struct inode *inode, struct f2fs_inode *ri)
|
|||
ri->i_inline |= F2FS_EXTRA_ATTR;
|
||||
if (is_inode_flag_set(inode, FI_PIN_FILE))
|
||||
ri->i_inline |= F2FS_PIN_FILE;
|
||||
if (is_inode_flag_set(inode, FI_COMPRESS_RELEASED))
|
||||
ri->i_inline |= F2FS_COMPRESS_RELEASED;
|
||||
}
|
||||
|
||||
static inline int f2fs_has_extra_attr(struct inode *inode)
|
||||
|
|
@ -3932,8 +3938,9 @@ static inline int f2fs_init_compress_mempool(void) { return 0; }
|
|||
static inline void f2fs_destroy_compress_mempool(void) { }
|
||||
#endif
|
||||
|
||||
static inline void set_compress_context(struct inode *inode)
|
||||
static inline int set_compress_context(struct inode *inode)
|
||||
{
|
||||
#ifdef CONFIG_F2FS_FS_COMPRESSION
|
||||
struct f2fs_sb_info *sbi = F2FS_I_SB(inode);
|
||||
|
||||
F2FS_I(inode)->i_compress_algorithm =
|
||||
|
|
@ -3946,19 +3953,25 @@ static inline void set_compress_context(struct inode *inode)
|
|||
set_inode_flag(inode, FI_COMPRESSED_FILE);
|
||||
stat_inc_compr_inode(inode);
|
||||
f2fs_mark_inode_dirty_sync(inode, true);
|
||||
return 0;
|
||||
#else
|
||||
return -EOPNOTSUPP;
|
||||
#endif
|
||||
}
|
||||
|
||||
static inline u64 f2fs_disable_compressed_file(struct inode *inode)
|
||||
static inline u32 f2fs_disable_compressed_file(struct inode *inode)
|
||||
{
|
||||
struct f2fs_inode_info *fi = F2FS_I(inode);
|
||||
u32 i_compr_blocks;
|
||||
|
||||
if (!f2fs_compressed_file(inode))
|
||||
return 0;
|
||||
if (S_ISREG(inode->i_mode)) {
|
||||
if (get_dirty_pages(inode))
|
||||
return 1;
|
||||
if (fi->i_compr_blocks)
|
||||
return fi->i_compr_blocks;
|
||||
i_compr_blocks = atomic_read(&fi->i_compr_blocks);
|
||||
if (i_compr_blocks)
|
||||
return i_compr_blocks;
|
||||
}
|
||||
|
||||
fi->i_flags &= ~F2FS_COMPR_FL;
|
||||
|
|
@ -4076,16 +4089,17 @@ static inline void f2fs_i_compr_blocks_update(struct inode *inode,
|
|||
u64 blocks, bool add)
|
||||
{
|
||||
int diff = F2FS_I(inode)->i_cluster_size - blocks;
|
||||
struct f2fs_inode_info *fi = F2FS_I(inode);
|
||||
|
||||
/* don't update i_compr_blocks if saved blocks were released */
|
||||
if (!add && !F2FS_I(inode)->i_compr_blocks)
|
||||
if (!add && !atomic_read(&fi->i_compr_blocks))
|
||||
return;
|
||||
|
||||
if (add) {
|
||||
F2FS_I(inode)->i_compr_blocks += diff;
|
||||
atomic_add(diff, &fi->i_compr_blocks);
|
||||
stat_add_compr_blocks(inode, diff);
|
||||
} else {
|
||||
F2FS_I(inode)->i_compr_blocks -= diff;
|
||||
atomic_sub(diff, &fi->i_compr_blocks);
|
||||
stat_sub_compr_blocks(inode, diff);
|
||||
}
|
||||
f2fs_mark_inode_dirty_sync(inode, true);
|
||||
|
|
|
|||
|
|
@ -58,6 +58,12 @@ static vm_fault_t f2fs_vm_page_mkwrite(struct vm_fault *vmf)
|
|||
bool need_alloc = true;
|
||||
int err = 0;
|
||||
|
||||
if (unlikely(IS_IMMUTABLE(inode)))
|
||||
return VM_FAULT_SIGBUS;
|
||||
|
||||
if (is_inode_flag_set(inode, FI_COMPRESS_RELEASED))
|
||||
return VM_FAULT_SIGBUS;
|
||||
|
||||
if (unlikely(f2fs_cp_error(sbi))) {
|
||||
err = -EIO;
|
||||
goto err;
|
||||
|
|
@ -80,10 +86,6 @@ static vm_fault_t f2fs_vm_page_mkwrite(struct vm_fault *vmf)
|
|||
err = ret;
|
||||
goto err;
|
||||
} else if (ret) {
|
||||
if (ret < F2FS_I(inode)->i_cluster_size) {
|
||||
err = -EAGAIN;
|
||||
goto err;
|
||||
}
|
||||
need_alloc = false;
|
||||
}
|
||||
}
|
||||
|
|
@ -258,8 +260,7 @@ static int f2fs_do_sync_file(struct file *file, loff_t start, loff_t end,
|
|||
};
|
||||
unsigned int seq_id = 0;
|
||||
|
||||
if (unlikely(f2fs_readonly(inode->i_sb) ||
|
||||
is_sbi_flag_set(sbi, SBI_CP_DISABLED)))
|
||||
if (unlikely(f2fs_readonly(inode->i_sb)))
|
||||
return 0;
|
||||
|
||||
trace_f2fs_sync_file_enter(inode);
|
||||
|
|
@ -273,7 +274,7 @@ static int f2fs_do_sync_file(struct file *file, loff_t start, loff_t end,
|
|||
ret = file_write_and_wait_range(file, start, end);
|
||||
clear_inode_flag(inode, FI_NEED_IPU);
|
||||
|
||||
if (ret) {
|
||||
if (ret || is_sbi_flag_set(sbi, SBI_CP_DISABLED)) {
|
||||
trace_f2fs_sync_file_exit(inode, cp_reason, datasync, ret);
|
||||
return ret;
|
||||
}
|
||||
|
|
@ -561,7 +562,7 @@ void f2fs_truncate_data_blocks_range(struct dnode_of_data *dn, int count)
|
|||
bool compressed_cluster = false;
|
||||
int cluster_index = 0, valid_blocks = 0;
|
||||
int cluster_size = F2FS_I(dn->inode)->i_cluster_size;
|
||||
bool released = !F2FS_I(dn->inode)->i_compr_blocks;
|
||||
bool released = !atomic_read(&F2FS_I(dn->inode)->i_compr_blocks);
|
||||
|
||||
if (IS_INODE(dn->node_page) && f2fs_has_extra_attr(dn->inode))
|
||||
base = get_extra_isize(dn->inode);
|
||||
|
|
@ -878,6 +879,14 @@ int f2fs_setattr(struct dentry *dentry, struct iattr *attr)
|
|||
if (unlikely(f2fs_cp_error(F2FS_I_SB(inode))))
|
||||
return -EIO;
|
||||
|
||||
if (unlikely(IS_IMMUTABLE(inode)))
|
||||
return -EPERM;
|
||||
|
||||
if (unlikely(IS_APPEND(inode) &&
|
||||
(attr->ia_valid & (ATTR_MODE | ATTR_UID |
|
||||
ATTR_GID | ATTR_TIMES_SET))))
|
||||
return -EPERM;
|
||||
|
||||
if ((attr->ia_valid & ATTR_SIZE) &&
|
||||
!f2fs_is_compress_backend_ready(inode))
|
||||
return -EOPNOTSUPP;
|
||||
|
|
@ -1850,8 +1859,8 @@ static int f2fs_setflags_common(struct inode *inode, u32 iflags, u32 mask)
|
|||
if (iflags & F2FS_COMPR_FL) {
|
||||
if (!f2fs_may_compress(inode))
|
||||
return -EINVAL;
|
||||
|
||||
set_compress_context(inode);
|
||||
if (set_compress_context(inode))
|
||||
return -EOPNOTSUPP;
|
||||
}
|
||||
}
|
||||
if ((iflags ^ masked_flags) & F2FS_NOCOMP_FL) {
|
||||
|
|
@ -3445,7 +3454,7 @@ static int f2fs_get_compress_blocks(struct file *filp, unsigned long arg)
|
|||
if (!f2fs_compressed_file(inode))
|
||||
return -EINVAL;
|
||||
|
||||
blocks = F2FS_I(inode)->i_compr_blocks;
|
||||
blocks = atomic_read(&F2FS_I(inode)->i_compr_blocks);
|
||||
return put_user(blocks, (u64 __user *)arg);
|
||||
}
|
||||
|
||||
|
|
@ -3535,7 +3544,7 @@ static int f2fs_release_compress_blocks(struct file *filp, unsigned long arg)
|
|||
goto out;
|
||||
}
|
||||
|
||||
if (IS_IMMUTABLE(inode)) {
|
||||
if (is_inode_flag_set(inode, FI_COMPRESS_RELEASED)) {
|
||||
ret = -EINVAL;
|
||||
goto out;
|
||||
}
|
||||
|
|
@ -3544,14 +3553,13 @@ static int f2fs_release_compress_blocks(struct file *filp, unsigned long arg)
|
|||
if (ret)
|
||||
goto out;
|
||||
|
||||
if (!F2FS_I(inode)->i_compr_blocks)
|
||||
goto out;
|
||||
|
||||
F2FS_I(inode)->i_flags |= F2FS_IMMUTABLE_FL;
|
||||
f2fs_set_inode_flags(inode);
|
||||
set_inode_flag(inode, FI_COMPRESS_RELEASED);
|
||||
inode->i_ctime = current_time(inode);
|
||||
f2fs_mark_inode_dirty_sync(inode, true);
|
||||
|
||||
if (!atomic_read(&F2FS_I(inode)->i_compr_blocks))
|
||||
goto out;
|
||||
|
||||
down_write(&F2FS_I(inode)->i_gc_rwsem[WRITE]);
|
||||
down_write(&F2FS_I(inode)->i_mmap_sem);
|
||||
|
||||
|
|
@ -3597,14 +3605,15 @@ out:
|
|||
|
||||
if (ret >= 0) {
|
||||
ret = put_user(released_blocks, (u64 __user *)arg);
|
||||
} else if (released_blocks && F2FS_I(inode)->i_compr_blocks) {
|
||||
} else if (released_blocks &&
|
||||
atomic_read(&F2FS_I(inode)->i_compr_blocks)) {
|
||||
set_sbi_flag(sbi, SBI_NEED_FSCK);
|
||||
f2fs_warn(sbi, "%s: partial blocks were released i_ino=%lx "
|
||||
"iblocks=%llu, released=%u, compr_blocks=%llu, "
|
||||
"iblocks=%llu, released=%u, compr_blocks=%u, "
|
||||
"run fsck to fix.",
|
||||
__func__, inode->i_ino, inode->i_blocks,
|
||||
released_blocks,
|
||||
F2FS_I(inode)->i_compr_blocks);
|
||||
atomic_read(&F2FS_I(inode)->i_compr_blocks));
|
||||
}
|
||||
|
||||
return ret;
|
||||
|
|
@ -3692,14 +3701,14 @@ static int f2fs_reserve_compress_blocks(struct file *filp, unsigned long arg)
|
|||
if (ret)
|
||||
return ret;
|
||||
|
||||
if (F2FS_I(inode)->i_compr_blocks)
|
||||
if (atomic_read(&F2FS_I(inode)->i_compr_blocks))
|
||||
goto out;
|
||||
|
||||
f2fs_balance_fs(F2FS_I_SB(inode), true);
|
||||
|
||||
inode_lock(inode);
|
||||
|
||||
if (!IS_IMMUTABLE(inode)) {
|
||||
if (!is_inode_flag_set(inode, FI_COMPRESS_RELEASED)) {
|
||||
ret = -EINVAL;
|
||||
goto unlock_inode;
|
||||
}
|
||||
|
|
@ -3744,8 +3753,7 @@ static int f2fs_reserve_compress_blocks(struct file *filp, unsigned long arg)
|
|||
up_write(&F2FS_I(inode)->i_mmap_sem);
|
||||
|
||||
if (ret >= 0) {
|
||||
F2FS_I(inode)->i_flags &= ~F2FS_IMMUTABLE_FL;
|
||||
f2fs_set_inode_flags(inode);
|
||||
clear_inode_flag(inode, FI_COMPRESS_RELEASED);
|
||||
inode->i_ctime = current_time(inode);
|
||||
f2fs_mark_inode_dirty_sync(inode, true);
|
||||
}
|
||||
|
|
@ -3756,14 +3764,15 @@ out:
|
|||
|
||||
if (ret >= 0) {
|
||||
ret = put_user(reserved_blocks, (u64 __user *)arg);
|
||||
} else if (reserved_blocks && F2FS_I(inode)->i_compr_blocks) {
|
||||
} else if (reserved_blocks &&
|
||||
atomic_read(&F2FS_I(inode)->i_compr_blocks)) {
|
||||
set_sbi_flag(sbi, SBI_NEED_FSCK);
|
||||
f2fs_warn(sbi, "%s: partial blocks were released i_ino=%lx "
|
||||
"iblocks=%llu, reserved=%u, compr_blocks=%llu, "
|
||||
"iblocks=%llu, reserved=%u, compr_blocks=%u, "
|
||||
"run fsck to fix.",
|
||||
__func__, inode->i_ino, inode->i_blocks,
|
||||
reserved_blocks,
|
||||
F2FS_I(inode)->i_compr_blocks);
|
||||
atomic_read(&F2FS_I(inode)->i_compr_blocks));
|
||||
}
|
||||
|
||||
return ret;
|
||||
|
|
@ -3902,6 +3911,16 @@ static ssize_t f2fs_file_write_iter(struct kiocb *iocb, struct iov_iter *from)
|
|||
inode_lock(inode);
|
||||
}
|
||||
|
||||
if (unlikely(IS_IMMUTABLE(inode))) {
|
||||
ret = -EPERM;
|
||||
goto unlock;
|
||||
}
|
||||
|
||||
if (is_inode_flag_set(inode, FI_COMPRESS_RELEASED)) {
|
||||
ret = -EPERM;
|
||||
goto unlock;
|
||||
}
|
||||
|
||||
ret = generic_write_checks(iocb, from);
|
||||
if (ret > 0) {
|
||||
bool preallocated = false;
|
||||
|
|
@ -3966,6 +3985,7 @@ write:
|
|||
if (ret > 0)
|
||||
f2fs_update_iostat(F2FS_I_SB(inode), APP_WRITE_IO, ret);
|
||||
}
|
||||
unlock:
|
||||
inode_unlock(inode);
|
||||
out:
|
||||
trace_f2fs_file_write_iter(inode, iocb->ki_pos,
|
||||
|
|
|
|||
|
|
@ -442,7 +442,8 @@ static int do_read_inode(struct inode *inode)
|
|||
(fi->i_flags & F2FS_COMPR_FL)) {
|
||||
if (F2FS_FITS_IN_INODE(ri, fi->i_extra_isize,
|
||||
i_log_cluster_size)) {
|
||||
fi->i_compr_blocks = le64_to_cpu(ri->i_compr_blocks);
|
||||
atomic_set(&fi->i_compr_blocks,
|
||||
le64_to_cpu(ri->i_compr_blocks));
|
||||
fi->i_compress_algorithm = ri->i_compress_algorithm;
|
||||
fi->i_log_cluster_size = ri->i_log_cluster_size;
|
||||
fi->i_cluster_size = 1 << fi->i_log_cluster_size;
|
||||
|
|
@ -460,7 +461,7 @@ static int do_read_inode(struct inode *inode)
|
|||
stat_inc_inline_inode(inode);
|
||||
stat_inc_inline_dir(inode);
|
||||
stat_inc_compr_inode(inode);
|
||||
stat_add_compr_blocks(inode, F2FS_I(inode)->i_compr_blocks);
|
||||
stat_add_compr_blocks(inode, atomic_read(&fi->i_compr_blocks));
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
@ -619,7 +620,8 @@ void f2fs_update_inode(struct inode *inode, struct page *node_page)
|
|||
F2FS_FITS_IN_INODE(ri, F2FS_I(inode)->i_extra_isize,
|
||||
i_log_cluster_size)) {
|
||||
ri->i_compr_blocks =
|
||||
cpu_to_le64(F2FS_I(inode)->i_compr_blocks);
|
||||
cpu_to_le64(atomic_read(
|
||||
&F2FS_I(inode)->i_compr_blocks));
|
||||
ri->i_compress_algorithm =
|
||||
F2FS_I(inode)->i_compress_algorithm;
|
||||
ri->i_log_cluster_size =
|
||||
|
|
@ -782,7 +784,8 @@ no_delete:
|
|||
stat_dec_inline_dir(inode);
|
||||
stat_dec_inline_inode(inode);
|
||||
stat_dec_compr_inode(inode);
|
||||
stat_sub_compr_blocks(inode, F2FS_I(inode)->i_compr_blocks);
|
||||
stat_sub_compr_blocks(inode,
|
||||
atomic_read(&F2FS_I(inode)->i_compr_blocks));
|
||||
|
||||
if (likely(!f2fs_cp_error(sbi) &&
|
||||
!is_sbi_flag_set(sbi, SBI_CP_DISABLED)))
|
||||
|
|
|
|||
|
|
@ -1054,6 +1054,7 @@ static struct inode *f2fs_alloc_inode(struct super_block *sb)
|
|||
|
||||
/* Initialize f2fs-specific inode info */
|
||||
atomic_set(&fi->dirty_pages, 0);
|
||||
atomic_set(&fi->i_compr_blocks, 0);
|
||||
init_rwsem(&fi->i_sem);
|
||||
spin_lock_init(&fi->i_size_lock);
|
||||
INIT_LIST_HEAD(&fi->dirty_list);
|
||||
|
|
@ -1779,6 +1780,18 @@ restore_flag:
|
|||
|
||||
static void f2fs_enable_checkpoint(struct f2fs_sb_info *sbi)
|
||||
{
|
||||
int retry = DEFAULT_RETRY_IO_COUNT;
|
||||
|
||||
/* we should flush all the data to keep data consistency */
|
||||
do {
|
||||
sync_inodes_sb(sbi->sb);
|
||||
cond_resched();
|
||||
congestion_wait(BLK_RW_ASYNC, DEFAULT_IO_TIMEOUT);
|
||||
} while (get_pages(sbi, F2FS_DIRTY_DATA) && retry--);
|
||||
|
||||
if (unlikely(retry < 0))
|
||||
f2fs_warn(sbi, "checkpoint=enable has some unwritten data.");
|
||||
|
||||
down_write(&sbi->gc_lock);
|
||||
f2fs_dirty_to_prefree(sbi);
|
||||
|
||||
|
|
@ -3903,6 +3916,8 @@ free_node_inode:
|
|||
free_stats:
|
||||
f2fs_destroy_stats(sbi);
|
||||
free_nm:
|
||||
/* stop discard thread before destroying node manager */
|
||||
f2fs_stop_discard_thread(sbi);
|
||||
f2fs_destroy_node_manager(sbi);
|
||||
free_sm:
|
||||
f2fs_destroy_segment_manager(sbi);
|
||||
|
|
|
|||
Loading…
Reference in a new issue