]> git.proxmox.com Git - mirror_zfs.git/commit
Fix read errors race after block cloning
authorAlexander Motin <mav@FreeBSD.org>
Mon, 8 Apr 2024 19:03:18 +0000 (15:03 -0400)
committerGitHub <noreply@github.com>
Mon, 8 Apr 2024 19:03:18 +0000 (12:03 -0700)
commiteeca9a91d6866879f4d57b4d0644e5da951f3daa
tree3b84a83e9f3b3be5666c6843a6314d33966df6db
parent76d1dde94ca9cac03fa641b4cf9259d98a706e12
Fix read errors race after block cloning

Investigating read errors triggering panic fixed in #16042 I've
found that we have a race in a sync process between the moment
dirty record for cloned block is removed and the moment dbuf is
destroyed.  If dmu_buf_hold_array_by_dnode() take a hold on a
cloned dbuf before it is synced/destroyed, then dbuf_read_impl()
may see it still in DB_NOFILL state, but without the dirty record.
Such case is not an error, but equivalent to DB_UNCACHED, since
the dbuf block pointer is already updated by dbuf_write_ready().
Unfortunately it is impossible to safely change the dbuf state
to DB_UNCACHED there, since there may already be another cloning
in progress, that dropped dbuf lock before creating a new dirty
record, protected only by the range lock.

Reviewed-by: Rob Norris <robn@despairlabs.com>
Reviewed-by: Robert Evans <evansr@google.com>
Signed-off-by: Alexander Motin <mav@FreeBSD.org>
Sponsored by: iXsystems, Inc.
Closes #16052
module/zfs/dbuf.c