btrfs: factor out common part of btrfs_{mknod,create,mkdir}()
btrfs_{mknod,create,mkdir}() are now identical other than the inode initialization and some inconsequential function call order differences. Factor out the common code to reduce code duplication. Reviewed-by: Sweet Tea Dorminy <sweettea-kernel@dorminy.me> Signed-off-by: Omar Sandoval <osandov@fb.com> Signed-off-by: David Sterba <dsterba@suse.com>
This commit is contained in:
Родитель
a1fd0c35ff
Коммит
5f465bf1f1
152
fs/btrfs/inode.c
152
fs/btrfs/inode.c
|
@ -6326,82 +6326,15 @@ fail_dir_item:
|
|||
return ret;
|
||||
}
|
||||
|
||||
static int btrfs_mknod(struct user_namespace *mnt_userns, struct inode *dir,
|
||||
struct dentry *dentry, umode_t mode, dev_t rdev)
|
||||
static int btrfs_create_common(struct inode *dir, struct dentry *dentry,
|
||||
struct inode *inode)
|
||||
{
|
||||
struct btrfs_fs_info *fs_info = btrfs_sb(dir->i_sb);
|
||||
struct btrfs_trans_handle *trans;
|
||||
struct btrfs_root *root = BTRFS_I(dir)->root;
|
||||
struct inode *inode;
|
||||
struct btrfs_trans_handle *trans;
|
||||
int err;
|
||||
u64 index = 0;
|
||||
|
||||
inode = new_inode(dir->i_sb);
|
||||
if (!inode)
|
||||
return -ENOMEM;
|
||||
inode_init_owner(mnt_userns, inode, dir, mode);
|
||||
inode->i_op = &btrfs_special_inode_operations;
|
||||
init_special_inode(inode, inode->i_mode, rdev);
|
||||
|
||||
/*
|
||||
* 2 for inode item and ref
|
||||
* 2 for dir items
|
||||
* 1 for xattr if selinux is on
|
||||
*/
|
||||
trans = btrfs_start_transaction(root, 5);
|
||||
if (IS_ERR(trans)) {
|
||||
iput(inode);
|
||||
return PTR_ERR(trans);
|
||||
}
|
||||
|
||||
err = btrfs_new_inode(trans, root, inode, dir, dentry->d_name.name,
|
||||
dentry->d_name.len, &index);
|
||||
if (err) {
|
||||
iput(inode);
|
||||
inode = NULL;
|
||||
goto out_unlock;
|
||||
}
|
||||
|
||||
err = btrfs_init_inode_security(trans, inode, dir, &dentry->d_name);
|
||||
if (err)
|
||||
goto out_unlock;
|
||||
|
||||
err = btrfs_add_link(trans, BTRFS_I(dir), BTRFS_I(inode),
|
||||
dentry->d_name.name, dentry->d_name.len, 0, index);
|
||||
if (err)
|
||||
goto out_unlock;
|
||||
|
||||
btrfs_update_inode(trans, root, BTRFS_I(inode));
|
||||
d_instantiate_new(dentry, inode);
|
||||
|
||||
out_unlock:
|
||||
btrfs_end_transaction(trans);
|
||||
btrfs_btree_balance_dirty(fs_info);
|
||||
if (err && inode) {
|
||||
inode_dec_link_count(inode);
|
||||
discard_new_inode(inode);
|
||||
}
|
||||
return err;
|
||||
}
|
||||
|
||||
static int btrfs_create(struct user_namespace *mnt_userns, struct inode *dir,
|
||||
struct dentry *dentry, umode_t mode, bool excl)
|
||||
{
|
||||
struct btrfs_fs_info *fs_info = btrfs_sb(dir->i_sb);
|
||||
struct btrfs_trans_handle *trans;
|
||||
struct btrfs_root *root = BTRFS_I(dir)->root;
|
||||
struct inode *inode;
|
||||
int err;
|
||||
u64 index = 0;
|
||||
|
||||
inode = new_inode(dir->i_sb);
|
||||
if (!inode)
|
||||
return -ENOMEM;
|
||||
inode_init_owner(mnt_userns, inode, dir, mode);
|
||||
inode->i_fop = &btrfs_file_operations;
|
||||
inode->i_op = &btrfs_file_inode_operations;
|
||||
inode->i_mapping->a_ops = &btrfs_aops;
|
||||
|
||||
/*
|
||||
* 2 for inode item and ref
|
||||
* 2 for dir items
|
||||
|
@ -6446,6 +6379,35 @@ out_unlock:
|
|||
return err;
|
||||
}
|
||||
|
||||
static int btrfs_mknod(struct user_namespace *mnt_userns, struct inode *dir,
|
||||
struct dentry *dentry, umode_t mode, dev_t rdev)
|
||||
{
|
||||
struct inode *inode;
|
||||
|
||||
inode = new_inode(dir->i_sb);
|
||||
if (!inode)
|
||||
return -ENOMEM;
|
||||
inode_init_owner(mnt_userns, inode, dir, mode);
|
||||
inode->i_op = &btrfs_special_inode_operations;
|
||||
init_special_inode(inode, inode->i_mode, rdev);
|
||||
return btrfs_create_common(dir, dentry, inode);
|
||||
}
|
||||
|
||||
static int btrfs_create(struct user_namespace *mnt_userns, struct inode *dir,
|
||||
struct dentry *dentry, umode_t mode, bool excl)
|
||||
{
|
||||
struct inode *inode;
|
||||
|
||||
inode = new_inode(dir->i_sb);
|
||||
if (!inode)
|
||||
return -ENOMEM;
|
||||
inode_init_owner(mnt_userns, inode, dir, mode);
|
||||
inode->i_fop = &btrfs_file_operations;
|
||||
inode->i_op = &btrfs_file_inode_operations;
|
||||
inode->i_mapping->a_ops = &btrfs_aops;
|
||||
return btrfs_create_common(dir, dentry, inode);
|
||||
}
|
||||
|
||||
static int btrfs_link(struct dentry *old_dentry, struct inode *dir,
|
||||
struct dentry *dentry)
|
||||
{
|
||||
|
@ -6527,12 +6489,7 @@ fail:
|
|||
static int btrfs_mkdir(struct user_namespace *mnt_userns, struct inode *dir,
|
||||
struct dentry *dentry, umode_t mode)
|
||||
{
|
||||
struct btrfs_fs_info *fs_info = btrfs_sb(dir->i_sb);
|
||||
struct inode *inode;
|
||||
struct btrfs_trans_handle *trans;
|
||||
struct btrfs_root *root = BTRFS_I(dir)->root;
|
||||
int err;
|
||||
u64 index = 0;
|
||||
|
||||
inode = new_inode(dir->i_sb);
|
||||
if (!inode)
|
||||
|
@ -6540,50 +6497,7 @@ static int btrfs_mkdir(struct user_namespace *mnt_userns, struct inode *dir,
|
|||
inode_init_owner(mnt_userns, inode, dir, S_IFDIR | mode);
|
||||
inode->i_op = &btrfs_dir_inode_operations;
|
||||
inode->i_fop = &btrfs_dir_file_operations;
|
||||
|
||||
/*
|
||||
* 2 items for inode and ref
|
||||
* 2 items for dir items
|
||||
* 1 for xattr if selinux is on
|
||||
*/
|
||||
trans = btrfs_start_transaction(root, 5);
|
||||
if (IS_ERR(trans)) {
|
||||
iput(inode);
|
||||
return PTR_ERR(trans);
|
||||
}
|
||||
|
||||
err = btrfs_new_inode(trans, root, inode, dir, dentry->d_name.name,
|
||||
dentry->d_name.len, &index);
|
||||
if (err) {
|
||||
iput(inode);
|
||||
inode = NULL;
|
||||
goto out_fail;
|
||||
}
|
||||
|
||||
err = btrfs_init_inode_security(trans, inode, dir, &dentry->d_name);
|
||||
if (err)
|
||||
goto out_fail;
|
||||
|
||||
err = btrfs_update_inode(trans, root, BTRFS_I(inode));
|
||||
if (err)
|
||||
goto out_fail;
|
||||
|
||||
err = btrfs_add_link(trans, BTRFS_I(dir), BTRFS_I(inode),
|
||||
dentry->d_name.name,
|
||||
dentry->d_name.len, 0, index);
|
||||
if (err)
|
||||
goto out_fail;
|
||||
|
||||
d_instantiate_new(dentry, inode);
|
||||
|
||||
out_fail:
|
||||
btrfs_end_transaction(trans);
|
||||
if (err && inode) {
|
||||
inode_dec_link_count(inode);
|
||||
discard_new_inode(inode);
|
||||
}
|
||||
btrfs_btree_balance_dirty(fs_info);
|
||||
return err;
|
||||
return btrfs_create_common(dir, dentry, inode);
|
||||
}
|
||||
|
||||
static noinline int uncompress_inline(struct btrfs_path *path,
|
||||
|
|
Загрузка…
Ссылка в новой задаче