mirror of
https://git.proxmox.com/git/mirror_zfs.git
synced 2024-12-27 03:19:35 +03:00
Fix negative zio->io_error which must be positive.
All the upper layers of zfs expect zio->io_error to be positive. I was careful but I missed one instance in vdev_disk_physio_completion() which could return a negative error. To ensure all cases are always caught I had additionally added an ASSERT() to check this before zio_interpret(). Finally, as a debugging aid when zfs is build with --enable-debug all errors from the backing block devices will be reported to the console with an error message like this: ZFS: zio error=5 type=1 offset=4217856 size=8192 flags=60440
This commit is contained in:
parent
398f129ca3
commit
d148e95156
@ -91,6 +91,17 @@ bdev_capacity(struct block_device *bdev)
|
|||||||
return get_capacity(bdev->bd_disk);
|
return get_capacity(bdev->bd_disk);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
vdev_disk_error(zio_t *zio)
|
||||||
|
{
|
||||||
|
#ifdef ZFS_DEBUG
|
||||||
|
printk("ZFS: zio error=%d type=%d offset=%llu "
|
||||||
|
"size=%llu flags=%x\n", zio->io_error, zio->io_type,
|
||||||
|
(u_longlong_t)zio->io_offset, (u_longlong_t)zio->io_size,
|
||||||
|
zio->io_flags);
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
static int
|
static int
|
||||||
vdev_disk_open(vdev_t *v, uint64_t *psize, uint64_t *ashift)
|
vdev_disk_open(vdev_t *v, uint64_t *psize, uint64_t *ashift)
|
||||||
{
|
{
|
||||||
@ -232,6 +243,9 @@ vdev_disk_dio_put(dio_request_t *dr)
|
|||||||
|
|
||||||
if (zio) {
|
if (zio) {
|
||||||
zio->io_error = error;
|
zio->io_error = error;
|
||||||
|
ASSERT3S(zio->io_error, >=, 0);
|
||||||
|
if (zio->io_error)
|
||||||
|
vdev_disk_error(zio);
|
||||||
zio_interrupt(zio);
|
zio_interrupt(zio);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -259,10 +273,10 @@ BIO_END_IO_PROTO(vdev_disk_physio_completion, bio, size, error)
|
|||||||
#endif /* HAVE_2ARGS_BIO_END_IO_T */
|
#endif /* HAVE_2ARGS_BIO_END_IO_T */
|
||||||
|
|
||||||
if (error == 0 && !test_bit(BIO_UPTODATE, &bio->bi_flags))
|
if (error == 0 && !test_bit(BIO_UPTODATE, &bio->bi_flags))
|
||||||
error = EIO;
|
error = -EIO;
|
||||||
|
|
||||||
if (dr->dr_error == 0)
|
if (dr->dr_error == 0)
|
||||||
dr->dr_error = error;
|
dr->dr_error = -error;
|
||||||
|
|
||||||
/* Drop reference aquired by __vdev_disk_physio */
|
/* Drop reference aquired by __vdev_disk_physio */
|
||||||
rc = vdev_disk_dio_put(dr);
|
rc = vdev_disk_dio_put(dr);
|
||||||
@ -434,6 +448,9 @@ BIO_END_IO_PROTO(vdev_disk_io_flush_completion, bio, size, rc)
|
|||||||
zio->io_vd->vdev_nowritecache = B_TRUE;
|
zio->io_vd->vdev_nowritecache = B_TRUE;
|
||||||
|
|
||||||
bio_put(bio);
|
bio_put(bio);
|
||||||
|
ASSERT3S(zio->io_error, >=, 0);
|
||||||
|
if (zio->io_error)
|
||||||
|
vdev_disk_error(zio);
|
||||||
zio_interrupt(zio);
|
zio_interrupt(zio);
|
||||||
|
|
||||||
BIO_END_IO_RETURN(0);
|
BIO_END_IO_RETURN(0);
|
||||||
|
Loading…
Reference in New Issue
Block a user