ext4: let ext4_delete_entry() handle inline data
Signed-off-by: Tao Ma <boyu.mt@taobao.com> Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
This commit is contained in:
parent
05019a9e7f
commit
9f40fe5463
|
@ -1510,6 +1510,61 @@ out_find:
|
|||
return iloc.bh;
|
||||
}
|
||||
|
||||
int ext4_delete_inline_entry(handle_t *handle,
|
||||
struct inode *dir,
|
||||
struct ext4_dir_entry_2 *de_del,
|
||||
struct buffer_head *bh,
|
||||
int *has_inline_data)
|
||||
{
|
||||
int err, inline_size;
|
||||
struct ext4_iloc iloc;
|
||||
void *inline_start;
|
||||
|
||||
err = ext4_get_inode_loc(dir, &iloc);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
down_write(&EXT4_I(dir)->xattr_sem);
|
||||
if (!ext4_has_inline_data(dir)) {
|
||||
*has_inline_data = 0;
|
||||
goto out;
|
||||
}
|
||||
|
||||
if ((void *)de_del - ((void *)ext4_raw_inode(&iloc)->i_block) <
|
||||
EXT4_MIN_INLINE_DATA_SIZE) {
|
||||
inline_start = (void *)ext4_raw_inode(&iloc)->i_block +
|
||||
EXT4_INLINE_DOTDOT_SIZE;
|
||||
inline_size = EXT4_MIN_INLINE_DATA_SIZE -
|
||||
EXT4_INLINE_DOTDOT_SIZE;
|
||||
} else {
|
||||
inline_start = ext4_get_inline_xattr_pos(dir, &iloc);
|
||||
inline_size = ext4_get_inline_size(dir) -
|
||||
EXT4_MIN_INLINE_DATA_SIZE;
|
||||
}
|
||||
|
||||
err = ext4_journal_get_write_access(handle, bh);
|
||||
if (err)
|
||||
goto out;
|
||||
|
||||
err = ext4_generic_delete_entry(handle, dir, de_del, bh,
|
||||
inline_start, inline_size, 0);
|
||||
if (err)
|
||||
goto out;
|
||||
|
||||
BUFFER_TRACE(bh, "call ext4_handle_dirty_metadata");
|
||||
err = ext4_mark_inode_dirty(handle, dir);
|
||||
if (unlikely(err))
|
||||
goto out;
|
||||
|
||||
ext4_show_inline_dir(dir, iloc.bh, inline_start, inline_size);
|
||||
out:
|
||||
up_write(&EXT4_I(dir)->xattr_sem);
|
||||
brelse(iloc.bh);
|
||||
if (err != -ENOENT)
|
||||
ext4_std_error(dir->i_sb, err);
|
||||
return err;
|
||||
}
|
||||
|
||||
int ext4_destroy_inline_data(handle_t *handle, struct inode *inode)
|
||||
{
|
||||
int ret;
|
||||
|
|
|
@ -2158,6 +2158,14 @@ static int ext4_delete_entry(handle_t *handle,
|
|||
{
|
||||
int err, csum_size = 0;
|
||||
|
||||
if (ext4_has_inline_data(dir)) {
|
||||
int has_inline_data = 1;
|
||||
err = ext4_delete_inline_entry(handle, dir, de_del, bh,
|
||||
&has_inline_data);
|
||||
if (has_inline_data)
|
||||
return err;
|
||||
}
|
||||
|
||||
if (EXT4_HAS_RO_COMPAT_FEATURE(dir->i_sb,
|
||||
EXT4_FEATURE_RO_COMPAT_METADATA_CSUM))
|
||||
csum_size = sizeof(struct ext4_dir_entry_tail);
|
||||
|
|
|
@ -175,6 +175,11 @@ extern struct buffer_head *ext4_find_inline_entry(struct inode *dir,
|
|||
const struct qstr *d_name,
|
||||
struct ext4_dir_entry_2 **res_dir,
|
||||
int *has_inline_data);
|
||||
extern int ext4_delete_inline_entry(handle_t *handle,
|
||||
struct inode *dir,
|
||||
struct ext4_dir_entry_2 *de_del,
|
||||
struct buffer_head *bh,
|
||||
int *has_inline_data);
|
||||
# else /* CONFIG_EXT4_FS_XATTR */
|
||||
|
||||
static inline int
|
||||
|
@ -368,6 +373,14 @@ ext4_find_inline_entry(struct inode *dir,
|
|||
{
|
||||
return NULL;
|
||||
}
|
||||
static inline int ext4_delete_inline_entry(handle_t *handle,
|
||||
struct inode *dir,
|
||||
struct ext4_dir_entry_2 *de_del,
|
||||
struct buffer_head *bh,
|
||||
int *has_inline_data)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
# endif /* CONFIG_EXT4_FS_XATTR */
|
||||
|
||||
#ifdef CONFIG_EXT4_FS_SECURITY
|
||||
|
|
Loading…
Reference in New Issue