1

ext4: get rid of ppath in ext4_ext_convert_to_initialized()

The use of path and ppath is now very confusing, so to make the code more
readable, pass path between functions uniformly, and get rid of ppath.

To get rid of the ppath in ext4_ext_convert_to_initialized(), the following
is done here:

 * Free the extents path when an error is encountered.
 * Its caller needs to update ppath if it uses ppath.
 * The 'allocated' is changed from passing a value to passing an address.

No functional changes.

Signed-off-by: Baokun Li <libaokun1@huawei.com>
Reviewed-by: Jan Kara <jack@suse.cz>
Reviewed-by: Ojaswin Mujoo <ojaswin@linux.ibm.com>
Tested-by: Ojaswin Mujoo <ojaswin@linux.ibm.com>
Link: https://patch.msgid.link/20240822023545.1994557-21-libaokun@huaweicloud.com
Signed-off-by: Theodore Ts'o <tytso@mit.edu>
This commit is contained in:
Baokun Li 2024-08-22 10:35:40 +08:00 committed by Theodore Ts'o
parent 8d5ad7b08f
commit 33c14b8bd8

View File

@ -3438,13 +3438,11 @@ static struct ext4_ext_path *ext4_split_extent(handle_t *handle,
* that are allocated and initialized. * that are allocated and initialized.
* It is guaranteed to be >= map->m_len. * It is guaranteed to be >= map->m_len.
*/ */
static int ext4_ext_convert_to_initialized(handle_t *handle, static struct ext4_ext_path *
struct inode *inode, ext4_ext_convert_to_initialized(handle_t *handle, struct inode *inode,
struct ext4_map_blocks *map, struct ext4_map_blocks *map, struct ext4_ext_path *path,
struct ext4_ext_path **ppath, int flags, unsigned int *allocated)
int flags)
{ {
struct ext4_ext_path *path = *ppath;
struct ext4_sb_info *sbi; struct ext4_sb_info *sbi;
struct ext4_extent_header *eh; struct ext4_extent_header *eh;
struct ext4_map_blocks split_map; struct ext4_map_blocks split_map;
@ -3454,7 +3452,6 @@ static int ext4_ext_convert_to_initialized(handle_t *handle,
unsigned int ee_len, depth, map_len = map->m_len; unsigned int ee_len, depth, map_len = map->m_len;
int err = 0; int err = 0;
int split_flag = EXT4_EXT_DATA_VALID2; int split_flag = EXT4_EXT_DATA_VALID2;
int allocated = 0;
unsigned int max_zeroout = 0; unsigned int max_zeroout = 0;
ext_debug(inode, "logical block %llu, max_blocks %u\n", ext_debug(inode, "logical block %llu, max_blocks %u\n",
@ -3495,6 +3492,7 @@ static int ext4_ext_convert_to_initialized(handle_t *handle,
* - L2: we only attempt to merge with an extent stored in the * - L2: we only attempt to merge with an extent stored in the
* same extent tree node. * same extent tree node.
*/ */
*allocated = 0;
if ((map->m_lblk == ee_block) && if ((map->m_lblk == ee_block) &&
/* See if we can merge left */ /* See if we can merge left */
(map_len < ee_len) && /*L1*/ (map_len < ee_len) && /*L1*/
@ -3524,7 +3522,7 @@ static int ext4_ext_convert_to_initialized(handle_t *handle,
(prev_len < (EXT_INIT_MAX_LEN - map_len))) { /*C4*/ (prev_len < (EXT_INIT_MAX_LEN - map_len))) { /*C4*/
err = ext4_ext_get_access(handle, inode, path + depth); err = ext4_ext_get_access(handle, inode, path + depth);
if (err) if (err)
goto out; goto errout;
trace_ext4_ext_convert_to_initialized_fastpath(inode, trace_ext4_ext_convert_to_initialized_fastpath(inode,
map, ex, abut_ex); map, ex, abut_ex);
@ -3539,7 +3537,7 @@ static int ext4_ext_convert_to_initialized(handle_t *handle,
abut_ex->ee_len = cpu_to_le16(prev_len + map_len); abut_ex->ee_len = cpu_to_le16(prev_len + map_len);
/* Result: number of initialized blocks past m_lblk */ /* Result: number of initialized blocks past m_lblk */
allocated = map_len; *allocated = map_len;
} }
} else if (((map->m_lblk + map_len) == (ee_block + ee_len)) && } else if (((map->m_lblk + map_len) == (ee_block + ee_len)) &&
(map_len < ee_len) && /*L1*/ (map_len < ee_len) && /*L1*/
@ -3570,7 +3568,7 @@ static int ext4_ext_convert_to_initialized(handle_t *handle,
(next_len < (EXT_INIT_MAX_LEN - map_len))) { /*C4*/ (next_len < (EXT_INIT_MAX_LEN - map_len))) { /*C4*/
err = ext4_ext_get_access(handle, inode, path + depth); err = ext4_ext_get_access(handle, inode, path + depth);
if (err) if (err)
goto out; goto errout;
trace_ext4_ext_convert_to_initialized_fastpath(inode, trace_ext4_ext_convert_to_initialized_fastpath(inode,
map, ex, abut_ex); map, ex, abut_ex);
@ -3585,18 +3583,20 @@ static int ext4_ext_convert_to_initialized(handle_t *handle,
abut_ex->ee_len = cpu_to_le16(next_len + map_len); abut_ex->ee_len = cpu_to_le16(next_len + map_len);
/* Result: number of initialized blocks past m_lblk */ /* Result: number of initialized blocks past m_lblk */
allocated = map_len; *allocated = map_len;
} }
} }
if (allocated) { if (*allocated) {
/* Mark the block containing both extents as dirty */ /* Mark the block containing both extents as dirty */
err = ext4_ext_dirty(handle, inode, path + depth); err = ext4_ext_dirty(handle, inode, path + depth);
/* Update path to point to the right extent */ /* Update path to point to the right extent */
path[depth].p_ext = abut_ex; path[depth].p_ext = abut_ex;
if (err)
goto errout;
goto out; goto out;
} else } else
allocated = ee_len - (map->m_lblk - ee_block); *allocated = ee_len - (map->m_lblk - ee_block);
WARN_ON(map->m_lblk < ee_block); WARN_ON(map->m_lblk < ee_block);
/* /*
@ -3623,21 +3623,21 @@ static int ext4_ext_convert_to_initialized(handle_t *handle,
split_map.m_lblk = map->m_lblk; split_map.m_lblk = map->m_lblk;
split_map.m_len = map->m_len; split_map.m_len = map->m_len;
if (max_zeroout && (allocated > split_map.m_len)) { if (max_zeroout && (*allocated > split_map.m_len)) {
if (allocated <= max_zeroout) { if (*allocated <= max_zeroout) {
/* case 3 or 5 */ /* case 3 or 5 */
zero_ex1.ee_block = zero_ex1.ee_block =
cpu_to_le32(split_map.m_lblk + cpu_to_le32(split_map.m_lblk +
split_map.m_len); split_map.m_len);
zero_ex1.ee_len = zero_ex1.ee_len =
cpu_to_le16(allocated - split_map.m_len); cpu_to_le16(*allocated - split_map.m_len);
ext4_ext_store_pblock(&zero_ex1, ext4_ext_store_pblock(&zero_ex1,
ext4_ext_pblock(ex) + split_map.m_lblk + ext4_ext_pblock(ex) + split_map.m_lblk +
split_map.m_len - ee_block); split_map.m_len - ee_block);
err = ext4_ext_zeroout(inode, &zero_ex1); err = ext4_ext_zeroout(inode, &zero_ex1);
if (err) if (err)
goto fallback; goto fallback;
split_map.m_len = allocated; split_map.m_len = *allocated;
} }
if (split_map.m_lblk - ee_block + split_map.m_len < if (split_map.m_lblk - ee_block + split_map.m_len <
max_zeroout) { max_zeroout) {
@ -3655,27 +3655,24 @@ static int ext4_ext_convert_to_initialized(handle_t *handle,
split_map.m_len += split_map.m_lblk - ee_block; split_map.m_len += split_map.m_lblk - ee_block;
split_map.m_lblk = ee_block; split_map.m_lblk = ee_block;
allocated = map->m_len; *allocated = map->m_len;
} }
} }
fallback: fallback:
path = ext4_split_extent(handle, inode, path, &split_map, split_flag, path = ext4_split_extent(handle, inode, path, &split_map, split_flag,
flags, NULL); flags, NULL);
if (IS_ERR(path)) { if (IS_ERR(path))
err = PTR_ERR(path); return path;
*ppath = NULL;
goto out;
}
err = 0;
*ppath = path;
out: out:
/* If we have gotten a failure, don't zero out status tree */ /* If we have gotten a failure, don't zero out status tree */
if (!err) { ext4_zeroout_es(inode, &zero_ex1);
ext4_zeroout_es(inode, &zero_ex1); ext4_zeroout_es(inode, &zero_ex2);
ext4_zeroout_es(inode, &zero_ex2); return path;
}
return err ? err : allocated; errout:
ext4_free_ext_path(path);
return ERR_PTR(err);
} }
/* /*
@ -3897,7 +3894,6 @@ ext4_ext_handle_unwritten_extents(handle_t *handle, struct inode *inode,
struct ext4_ext_path **ppath, int flags, struct ext4_ext_path **ppath, int flags,
unsigned int allocated, ext4_fsblk_t newblock) unsigned int allocated, ext4_fsblk_t newblock)
{ {
int ret = 0;
int err = 0; int err = 0;
ext_debug(inode, "logical block %llu, max_blocks %u, flags 0x%x, allocated %u\n", ext_debug(inode, "logical block %llu, max_blocks %u, flags 0x%x, allocated %u\n",
@ -3977,23 +3973,24 @@ ext4_ext_handle_unwritten_extents(handle_t *handle, struct inode *inode,
* For buffered writes, at writepage time, etc. Convert a * For buffered writes, at writepage time, etc. Convert a
* discovered unwritten extent to written. * discovered unwritten extent to written.
*/ */
ret = ext4_ext_convert_to_initialized(handle, inode, map, ppath, flags); *ppath = ext4_ext_convert_to_initialized(handle, inode, map, *ppath,
if (ret < 0) { flags, &allocated);
err = ret; if (IS_ERR(*ppath)) {
err = PTR_ERR(*ppath);
*ppath = NULL;
goto out2; goto out2;
} }
ext4_update_inode_fsync_trans(handle, inode, 1); ext4_update_inode_fsync_trans(handle, inode, 1);
/* /*
* shouldn't get a 0 return when converting an unwritten extent * shouldn't get a 0 allocated when converting an unwritten extent
* unless m_len is 0 (bug) or extent has been corrupted * unless m_len is 0 (bug) or extent has been corrupted
*/ */
if (unlikely(ret == 0)) { if (unlikely(allocated == 0)) {
EXT4_ERROR_INODE(inode, "unexpected ret == 0, m_len = %u", EXT4_ERROR_INODE(inode, "unexpected allocated == 0, m_len = %u",
map->m_len); map->m_len);
err = -EFSCORRUPTED; err = -EFSCORRUPTED;
goto out2; goto out2;
} }
allocated = ret;
out: out:
map->m_flags |= EXT4_MAP_NEW; map->m_flags |= EXT4_MAP_NEW;