mirror of
https://git.proxmox.com/git/mirror_zfs.git
synced 2026-05-22 10:37:35 +03:00
Fix regression in dmu_buf_will_fill()
Direct I/O implementation added condition to call dbuf_undirty() only in case of block cloning. But the condition is not right if the block is no longer dirty in this TXG, but still in DB_NOFILL state. It resulted in block not reverting to DB_UNCACHED and following NULL de-reference on attempt to access absent db_data. While there, add assertions for db_data to make debugging easier. Reviewed-by: Brian Atkinson <batkinson@lanl.gov> Reviewed-by: Brian Behlendorf <behlendorf1@llnl.gov> Signed-off-by: Alexander Motin <mav@FreeBSD.org> Sponsored by: iXsystems, Inc. Closes #16829
This commit is contained in:
committed by
Brian Behlendorf
parent
17cdb7a2b1
commit
b17ea73f9d
+1
-1
@@ -2921,7 +2921,7 @@ dmu_buf_will_fill(dmu_buf_t *db_fake, dmu_tx_t *tx, boolean_t canfail)
|
||||
* pending clone and mark the block as uncached. This will be
|
||||
* as if the clone was never done.
|
||||
*/
|
||||
if (dr && dr->dt.dl.dr_brtwrite) {
|
||||
if (db->db_state == DB_NOFILL) {
|
||||
VERIFY(!dbuf_undirty(db, tx));
|
||||
db->db_state = DB_UNCACHED;
|
||||
}
|
||||
|
||||
@@ -1221,6 +1221,7 @@ dmu_read_impl(dnode_t *dn, uint64_t offset, uint64_t size,
|
||||
bufoff = offset - db->db_offset;
|
||||
tocpy = MIN(db->db_size - bufoff, size);
|
||||
|
||||
ASSERT(db->db_data != NULL);
|
||||
(void) memcpy(buf, (char *)db->db_data + bufoff, tocpy);
|
||||
|
||||
offset += tocpy;
|
||||
@@ -1278,6 +1279,7 @@ dmu_write_impl(dmu_buf_t **dbp, int numbufs, uint64_t offset, uint64_t size,
|
||||
else
|
||||
dmu_buf_will_dirty(db, tx);
|
||||
|
||||
ASSERT(db->db_data != NULL);
|
||||
(void) memcpy((char *)db->db_data + bufoff, buf, tocpy);
|
||||
|
||||
if (tocpy == db->db_size)
|
||||
@@ -1426,6 +1428,7 @@ dmu_read_uio_dnode(dnode_t *dn, zfs_uio_t *uio, uint64_t size)
|
||||
bufoff = zfs_uio_offset(uio) - db->db_offset;
|
||||
tocpy = MIN(db->db_size - bufoff, size);
|
||||
|
||||
ASSERT(db->db_data != NULL);
|
||||
err = zfs_uio_fault_move((char *)db->db_data + bufoff, tocpy,
|
||||
UIO_READ, uio);
|
||||
|
||||
@@ -1550,6 +1553,7 @@ top:
|
||||
else
|
||||
dmu_buf_will_dirty(db, tx);
|
||||
|
||||
ASSERT(db->db_data != NULL);
|
||||
err = zfs_uio_fault_move((char *)db->db_data + bufoff,
|
||||
tocpy, UIO_WRITE, uio);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user