summaryrefslogtreecommitdiff
path: root/tools/perf/scripts/python/export-to-sqlite.py
diff options
context:
space:
mode:
authorBaokun Li <libaokun@linux.alibaba.com>2026-06-29 19:38:25 +0800
committerTheodore Ts'o <tytso@mit.edu>2026-07-22 11:45:37 -0400
commit07961ebb09c9c9fd7fd95fe9fa6d1455df41a7dd (patch)
tree7e624a3f5ea4cd34db427236e928fef267d1b351 /tools/perf/scripts/python/export-to-sqlite.py
parent63b314a7795e026424e5b3a4443f854c51c839f7 (diff)
ext4: base unaligned DIO lock decision on partial block zeroing
For unaligned DIO writes, the previous ext4_overwrite_io() required the entire range to fall within a single written extent. This was overly conservative: the DIO layer only performs partial block zeroing for the head and tail blocks when they are partially covered by the write. Middle blocks that are fully covered are written as whole blocks without any zeroing, so they are safe regardless of extent state. Therefore exclusive lock is only required when partial block zeroing will actually happen: - The head partial block (if any) lands on a hole or unwritten extent. - The tail partial block (if any) lands on a hole or unwritten extent. Middle full-cover blocks can be in any state (hole, unwritten, or written) - block allocation under shared lock is safe per the previous patch's analysis (inode_dio_begin + i_data_sem protection). Replace ext4_overwrite_io() with ext4_dio_needs_zeroing(), which directly answers the question driving the lock decision. It uses at most two ext4_map_blocks() calls: one for the head partial block (also catching the case where it spans through the tail), and one for the tail partial block if not already covered. This enables shared lock for previously-rejected scenarios such as: - Unaligned write spanning written extent + mid-range hole + written extent at the tail. - Unaligned write where the partial blocks land on written extents but the middle has unwritten extents. Performance: Hardware: /dev/sda (rotational disk, ~1 GB/s sustained write) Filesystem: ext4 default mkfs Unaligned DIO writes (14336 bytes at +512 within each 16K stripe). Each stripe is laid out as [written][unwritten][unwritten][written], so the head and tail partial blocks land on written extents but the middle is unwritten. Metric: IOPS. JOBS Before After speedup ---- -------- --------- ------- 1 15,547 17,381 1.12x 2 15,910 34,172 2.15x 4 15,014 57,567 3.83x 8 15,022 81,947 5.46x 16 14,586 99,126 6.80x 32 14,047 92,519 6.59x Wall time at JOBS=32: 149.3s (Before) -> 22.7s (After), 6.58x faster. Reviewed-by: Zhang Yi <yi.zhang@huawei.com> Reviewed-by: Jan Kara <jack@suse.cz> Signed-off-by: Baokun Li <libaokun@linux.alibaba.com> Link: https://patch.msgid.link/20260629113827.4074335-5-libaokun@linux.alibaba.com Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Diffstat (limited to 'tools/perf/scripts/python/export-to-sqlite.py')
0 files changed, 0 insertions, 0 deletions