From: Heming Zhao <heming.zhao@suse.com>
To: joseph.qi@linux.alibaba.com, mark@fasheh.com, jlbec@evilplan.org,
hch@lst.de
Cc: Heming Zhao <heming.zhao@suse.com>,
ocfs2-devel@lists.linux.dev, linux-kernel@vger.kernel.org
Subject: [RFC PATCH v3 0/4] migrates ocfs2 DIO from buffer_head to iomap
Date: Sun, 18 Oct 2026 22:33:12 +0800 [thread overview]
Message-ID: <20261018143319.22329-1-heming.zhao@suse.com> (raw)
This patch set migrates ocfs2 Direct I/O (DIO) from buffer_head mode
to iomap mode. And the code base is commit 58717b2a1365d.
Changelog:
v3:
patch 1/4
revise the commit log
for ocfs2_map_blocks():
- removed S_ISLNK() handling, as S_ISLNK inodes are already handled by the existing code path:
ocfs2_read_folio => block_read_full_folio() => get_block (ocfs2_get_block)
- replace "return -EIO" with "return err" at the end of this func
patch 2/4
revise the commit log based on hch's comments.
in ocfs2_iomap_begin(), replace the "/* todo */" comment under the IOMAP_WRITE case with "return -EOPNOTSUPP".
revise comments in ocfs2_iomap_dio_end_io()
remove the unused "bail" label in ocfs2_dio_end_io_r_pr()
patch 3/4
revise the commit log based on hch's comments.
remove the unused var max_blocks in ocfs2_iomap_dio_end_io_write().
followed Joseph's comment, directly set map.lblk in ocfs2_iomap_dio_end_io_write().
in ocfs2_dio_wr_map_blocks():
- replace BUG_ON(p_blkno == 0) with "ret = -EIO, mlog_errno() and goto unlock".
(the legacy code was copied from ocfs2_dio_wr_get_block())
- adjust arithmetic for map->len by substracting the offset and using min_t() to cap the length within limits.
- adjust error handling style for the return value of ocfs2_write_end_nolock().
introduce a new function, ocfs2_dio_zero_eof().
patch 4/4
Set f_mode with FMODE_CAN_ODIRECT only for non-inline files, per Joseph's comments.
v2:
- Merge Joseph's code and ideas from [1]:
- Add FMODE_CAN_ODIRECT to f_mode in ocfs2_file_open()
- Change iomap_ops and iomap_dio_ops API declarations from ocfs2.h to
aops.h
- Switch from iomap_dio_rw to __iomap_dio_rw + iomap_dio_complete
- Change "struct iomap_dio_ops" from read/write style to PR/EX locking
style. With this approach, we completely eliminate the need to define
any iocb->ki_flags bits.
- Remove alignment code from ocfs2_should_use_dio(), because iomap internally
already handles this.
- Add patch 4 to remove unused functions and the CONFIG_LEGACY_DIRECT_IO
Kconfig option.
- Add "Co-developed-by: Joseph Qi <joseph.qi@linux.alibaba.com>"
[1]:
https://gitee.com/anolis/storage-cloud-kernel/commit/ea3fe75e2060118ba093e90b1cd34fa382914b29
v1:
https://lore.kernel.org/ocfs2-devel/20260724052559.15409-1-heming.zhao@suse.com/
v2:
https://lore.kernel.org/ocfs2-devel/20260727061802.18485-1-heming.zhao@suse.com/
--------------
# test report
This patch set has been tested on 7.3.0-rc7 kernel with the following test
cases.
## ltp
runltp -f dio -d /mnt/ocfs2/
The test results: passed
## xfstests
format cmd: mkfs.ocfs2 -M local --fs-feature-level=max-features /dev/vde
./check -g quick -T -b -s ocfs2 -e generic/081 \
-e generic/266 -e generic/272 -e generic/281 \
-e generic/338 -e generic/347 -e generic/361 \
-e generic/628 -e generic/629 -e generic/648 -e generic/650
The test results are the same before and after the patch set.
Failures: generic/003 generic/091 generic/094 generic/177 generic/211
generic/225 generic/263 generic/322 generic/329 generic/331 generic/370
generic/376 generic/424 generic/448 generic/467 generic/477 generic/481
generic/510 generic/513 generic/537 generic/552 generic/563 generic/578
generic/607 generic/620 generic/630 generic/755 generic/760 generic/777
generic/784
Failed 30 of 631 tests
(following is 7.2.0 kernel test result)
Failures: generic/003 generic/322 generic/329 generic/331 generic/370
generic/376 generic/420 generic/424 generic/448 generic/449 generic/467
generic/477 generic/510 generic/513 generic/537 generic/552 generic/563
generic/578 generic/607 generic/620 generic/630 generic/755 generic/777
generic/784
Failed 24 of 632 tests
## fio on single node
(this is v2 test result, v3 test result is similar)
fio --direct=1 --iodepth=32 --rw=write --ioengine=libaio --bs=128k --size=1g \
--numjobs=4 --runtime=100 --group_reporting --filename=/mnt/ocfs2/write.1g --name=tst
- before patch : write: IOPS=18.8k, BW=4708MiB/s (4937MB/s)(4096MiB/870msec)
- applied patch: write: IOPS=39.6k, BW=4953MiB/s (5193MB/s)(4096MiB/827msec)
- overwrite (don't remove write.1g, run above fio command) speed seems same.
fio --direct=1 --iodepth=32 --rw=read --ioengine=libaio --bs=128k --size=1g \
--numjobs=4 --runtime=100 --group_reporting --filename=/mnt/ocfs2/write.1g --name=tst
- before patch : read: IOPS=52.4k, BW=6554MiB/s (6872MB/s)(4096MiB/625msec)
- applied patch: read: IOPS=52.2k, BW=6522MiB/s (6839MB/s)(4096MiB/628msec)
fio --direct=1 --iodepth=32 --rw=randwrite --ioengine=libaio --bs=4k --size=1g \
--numjobs=4 --runtime=100 --group_reporting --filename=/mnt/ocfs2/write.1g --name=tst
- before patch
- creating write: IOPS=20.9k, BW=81.7MiB/s (85.6MB/s)(4096MiB/50159msec)
- overwriting write.1g: write: IOPS=281k, BW=1097MiB/s (1151MB/s)(4096MiB/3733msec)
- applied patch
- creating write: IOPS=21.0k, BW=82.0MiB/s (86.0MB/s)(4096MiB/49938msec)
- overwriting write.1g: write: IOPS=329k, BW=1286MiB/s (1348MB/s)(4096MiB/3185msec)
fio --direct=1 --iodepth=32 --rw=randread --ioengine=libaio --bs=4k --size=1g \
--numjobs=4 --runtime=100 --group_reporting --filename=/mnt/ocfs2/write.1g --name=tst
- before patch : read: IOPS=372k, BW=1452MiB/s (1522MB/s)(4096MiB/2821msec)
- applied patch: read: IOPS=369k, BW=1441MiB/s (1511MB/s)(4096MiB/2842msec)
## fio on two nodes
### write in different folder
node1 /root/fio/diff/ocfs2-w.sh:
> fio --direct=1 --iodepth=32 --rw=write --ioengine=libaio --bs=128k --size=2g \
> --numjobs=2 --runtime=100 --group_reporting --filename=/mnt/ocfs2/node1/write.2g --name=tst
node2 /root/fio/diff/ocfs2-w.sh:
> fio --direct=1 --iodepth=32 --rw=write --ioengine=libaio --bs=128k --size=2g \
> --numjobs=2 --runtime=100 --group_reporting --filename=/mnt/ocfs2/node2/write.2g --name=tst
node1 /root/fio/diff/ocfs2-randw.sh:
> fio --direct=1 --iodepth=32 --rw=randwrite --ioengine=libaio --bs=4k --size=2g \
> --numjobs=2 --runtime=100 --group_reporting --filename=/mnt/ocfs2/node1/write.2g --name=tst
node2 /root/fio/diff/ocfs2-randw.sh:
> fio --direct=1 --iodepth=32 --rw=randwrite --ioengine=libaio --bs=4k --size=2g \
> --numjobs=2 --runtime=100 --group_reporting --filename=/mnt/ocfs2/node2/write.2g --name=tst
run on both node,
pdsh -w ssh:tw2510-[1-2] /root/fio/diff/ocfs2-w.sh
- before patch : write: IOPS=19.3k, BW=2417MiB/s (2534MB/s)(4096MiB/1695msec)
- applied patch: write: IOPS=20.8k, BW=2599MiB/s (2725MB/s)(4096MiB/1576msec)
pdsh -w ssh:tw2510-[1-2] /root/fio/diff/ocfs2-randw.sh
- before patch : write: IOPS=3742, BW=14.6MiB/s (15.3MB/s)(1462MiB/100007msec)
- applied patch: write: IOPS=3765, BW=14.7MiB/s (15.4MB/s)(1471MiB/100010msec)
### write in same file
node1 & node2: (/root/fio/share/ocfs2-w.sh)
fio --direct=1 --iodepth=32 --rw=write --ioengine=libaio --bs=128k --size=2g \
--numjobs=2 --runtime=100 --group_reporting --filename=/mnt/ocfs2/share/write.2g --name=tst
node1 & node2: (/root/fio/share/ocfs2-randw.sh)
fio --direct=1 --iodepth=32 --rw=randwrite --ioengine=libaio --bs=4k --size=2g \
--numjobs=2 --runtime=100 --group_reporting --filename=/mnt/ocfs2/share/write.2g --name=tst
run on both node
pdsh -w ssh:tw2510-[1-2] /root/fio/share/ocfs2-w.sh
- before patch : write: IOPS=2052, BW=257MiB/s (269MB/s)(4096MiB/15967msec)
- applied patch: write: IOPS=2558, BW=320MiB/s (335MB/s)(4096MiB/12808msec)
pdsh -w ssh:tw2510-[1-2] /root/fio/share/ocfs2-randw.sh
- before patch : write: IOPS=3588, BW=14.0MiB/s (14.7MB/s)(1402MiB/100001msec)
- applied patch: write: IOPS=3590, BW=14.0MiB/s (14.7MB/s)(1403MiB/100001msec)
Heming Zhao (4):
ocfs2: Add new ocfs2_map_blocks() to introduce iomap feature
ocfs2: switch DIO read path from buffer_head to iomap
ocfs2: switch dio write path from buffer_head to iomap
ocfs2: remove legacy blockdev direct-IO path APIs
fs/ocfs2/Kconfig | 2 +-
fs/ocfs2/aops.c | 689 ++++++++++++++++++++++++--------------
fs/ocfs2/aops.h | 38 +--
fs/ocfs2/buffer_head_io.c | 19 +-
fs/ocfs2/file.c | 168 ++++++++--
fs/ocfs2/ocfs2.h | 45 ++-
fs/ocfs2/ocfs2_fs.h | 3 +
7 files changed, 634 insertions(+), 330 deletions(-)
--
2.55.0
next reply other threads:[~2026-10-18 14:33 UTC|newest]
Thread overview: 5+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-10-18 14:33 Heming Zhao [this message]
2026-10-18 14:33 ` [RFC PATCH v3 1/4] ocfs2: Add new ocfs2_map_blocks() to introduce iomap feature Heming Zhao
2026-10-18 14:33 ` [RFC PATCH v3 2/4] ocfs2: switch DIO read path from buffer_head to iomap Heming Zhao
2026-10-18 14:33 ` [RFC PATCH v3 3/4] ocfs2: switch dio write " Heming Zhao
2026-10-18 14:33 ` [RFC PATCH v3 4/4] ocfs2: remove legacy blockdev direct-IO path APIs Heming Zhao
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20261018143319.22329-1-heming.zhao@suse.com \
--to=heming.zhao@suse.com \
--cc=hch@lst.de \
--cc=jlbec@evilplan.org \
--cc=joseph.qi@linux.alibaba.com \
--cc=linux-kernel@vger.kernel.org \
--cc=mark@fasheh.com \
--cc=ocfs2-devel@lists.linux.dev \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox
all inboxes | Powered by JetHome®