mirror of
https://mirrors.bfsu.edu.cn/git/linux.git
synced 2024-11-11 12:28:41 +08:00
ext2_rename(): set_link and delete_entry may fail
Signed-off-by: Al Viro <viro@zeniv.linux.org.uk> Reviewed-by: Fabio M. De Francesco <fmdefrancesco@gmail.com> Tested-by: Fabio M. De Francesco <fmdefrancesco@gmail.com> Signed-off-by: Jan Kara <jack@suse.cz>
This commit is contained in:
parent
6e335cd789
commit
8f1dca19b1
@ -606,8 +606,7 @@ int ext2_delete_entry (struct ext2_dir_entry_2 *dir, struct page *page,
|
||||
if (de->rec_len == 0) {
|
||||
ext2_error(inode->i_sb, __func__,
|
||||
"zero-length directory entry");
|
||||
err = -EIO;
|
||||
goto out;
|
||||
return -EIO;
|
||||
}
|
||||
pde = de;
|
||||
de = ext2_next_entry(de);
|
||||
@ -617,7 +616,10 @@ int ext2_delete_entry (struct ext2_dir_entry_2 *dir, struct page *page,
|
||||
pos = page_offset(page) + from;
|
||||
lock_page(page);
|
||||
err = ext2_prepare_chunk(page, pos, to - from);
|
||||
BUG_ON(err);
|
||||
if (err) {
|
||||
unlock_page(page);
|
||||
return err;
|
||||
}
|
||||
if (pde)
|
||||
pde->rec_len = ext2_rec_len_to_disk(to - from);
|
||||
dir->inode = 0;
|
||||
@ -625,9 +627,7 @@ int ext2_delete_entry (struct ext2_dir_entry_2 *dir, struct page *page,
|
||||
inode->i_ctime = inode->i_mtime = current_time(inode);
|
||||
EXT2_I(inode)->i_flags &= ~EXT2_BTREE_FL;
|
||||
mark_inode_dirty(inode);
|
||||
err = ext2_handle_dirsync(inode);
|
||||
out:
|
||||
return err;
|
||||
return ext2_handle_dirsync(inode);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -335,18 +335,16 @@ static int ext2_rename (struct mnt_idmap * idmap,
|
||||
|
||||
err = dquot_initialize(old_dir);
|
||||
if (err)
|
||||
goto out;
|
||||
return err;
|
||||
|
||||
err = dquot_initialize(new_dir);
|
||||
if (err)
|
||||
goto out;
|
||||
return err;
|
||||
|
||||
old_de = ext2_find_entry(old_dir, &old_dentry->d_name, &old_page,
|
||||
&old_page_addr);
|
||||
if (IS_ERR(old_de)) {
|
||||
err = PTR_ERR(old_de);
|
||||
goto out;
|
||||
}
|
||||
if (IS_ERR(old_de))
|
||||
return PTR_ERR(old_de);
|
||||
|
||||
if (S_ISDIR(old_inode->i_mode)) {
|
||||
err = -EIO;
|
||||
@ -394,27 +392,20 @@ static int ext2_rename (struct mnt_idmap * idmap,
|
||||
old_inode->i_ctime = current_time(old_inode);
|
||||
mark_inode_dirty(old_inode);
|
||||
|
||||
ext2_delete_entry(old_de, old_page, old_page_addr);
|
||||
|
||||
if (dir_de) {
|
||||
if (old_dir != new_dir) {
|
||||
err = ext2_delete_entry(old_de, old_page, old_page_addr);
|
||||
if (!err && dir_de) {
|
||||
if (old_dir != new_dir)
|
||||
err = ext2_set_link(old_inode, dir_de, dir_page,
|
||||
dir_page_addr, new_dir, false);
|
||||
|
||||
}
|
||||
ext2_put_page(dir_page, dir_page_addr);
|
||||
inode_dec_link_count(old_dir);
|
||||
}
|
||||
|
||||
out_old:
|
||||
ext2_put_page(old_page, old_page_addr);
|
||||
out:
|
||||
return err;
|
||||
|
||||
out_dir:
|
||||
if (dir_de)
|
||||
ext2_put_page(dir_page, dir_page_addr);
|
||||
goto out_old;
|
||||
out_old:
|
||||
ext2_put_page(old_page, old_page_addr);
|
||||
return err;
|
||||
}
|
||||
|
||||
const struct inode_operations ext2_dir_inode_operations = {
|
||||
|
Loading…
Reference in New Issue
Block a user