/*
* Macros to get and set fields in a bp or DVA.
*/
+
+/*
+ * Note, for gang blocks, DVA_GET_ASIZE() is the total space allocated for
+ * this gang DVA including its children BP's. The space allocated at this
+ * DVA's vdev/offset is vdev_gang_header_asize(vdev).
+ */
#define DVA_GET_ASIZE(dva) \
BF64_GET_SB((dva)->dva_word[0], 0, SPA_ASIZEBITS, SPA_MINBLOCKSHIFT, 0)
#define DVA_SET_ASIZE(dva, x) \
extern uint64_t vdev_psize_to_asize(vdev_t *vd, uint64_t psize);
+/*
+ * Return the amount of space allocated for a gang block header.
+ */
+static inline uint64_t
+vdev_gang_header_asize(vdev_t *vd)
+{
+ return (vdev_psize_to_asize(vd, SPA_GANGBLOCKSIZE));
+}
+
extern int vdev_fault(spa_t *spa, uint64_t guid, vdev_aux_t aux);
extern int vdev_degrade(spa_t *spa, uint64_t guid, vdev_aux_t aux);
extern int vdev_online(spa_t *spa, uint64_t guid, uint64_t flags,
ASSERT3P(vd->vdev_indirect_mapping, ==, NULL);
if (DVA_GET_GANG(dva))
- size = vdev_psize_to_asize(vd, SPA_GANGBLOCKSIZE);
+ size = vdev_gang_header_asize(vd);
msp = vd->vdev_ms[offset >> vd->vdev_ms_shift];
ASSERT3U(spa_config_held(spa, SCL_ALL, RW_READER), !=, 0);
if (DVA_GET_GANG(dva)) {
- size = vdev_psize_to_asize(vd, SPA_GANGBLOCKSIZE);
+ size = vdev_gang_header_asize(vd);
}
metaslab_free_impl(vd, offset, size, checkpoint);
ASSERT(DVA_IS_VALID(dva));
if (DVA_GET_GANG(dva))
- size = vdev_psize_to_asize(vd, SPA_GANGBLOCKSIZE);
+ size = vdev_gang_header_asize(vd);
return (metaslab_claim_impl(vd, offset, size, txg));
}
uint64_t size = DVA_GET_ASIZE(&bp->blk_dva[i]);
if (DVA_GET_GANG(&bp->blk_dva[i]))
- size = vdev_psize_to_asize(vd, SPA_GANGBLOCKSIZE);
+ size = vdev_gang_header_asize(vd);
ASSERT3P(vd, !=, NULL);
* that are in the log) to be arbitrarily large.
*/
for (int i = 0; i < BP_GET_NDVAS(bp); i++) {
- uint64_t vdevid = DVA_GET_VDEV(&bp->blk_dva[i]);
+ const dva_t *dva = &bp->blk_dva[i];
+ uint64_t vdevid = DVA_GET_VDEV(dva);
if (vdevid >= spa->spa_root_vdev->vdev_children) {
errors += zfs_blkptr_verify_log(spa, bp, blk_verify,
*/
continue;
}
- uint64_t offset = DVA_GET_OFFSET(&bp->blk_dva[i]);
- uint64_t asize = DVA_GET_ASIZE(&bp->blk_dva[i]);
- if (BP_IS_GANG(bp))
- asize = vdev_psize_to_asize(vd, SPA_GANGBLOCKSIZE);
+ uint64_t offset = DVA_GET_OFFSET(dva);
+ uint64_t asize = DVA_GET_ASIZE(dva);
+ if (DVA_GET_GANG(dva))
+ asize = vdev_gang_header_asize(vd);
if (offset + asize > vd->vdev_asize) {
errors += zfs_blkptr_verify_log(spa, bp, blk_verify,
"blkptr at %p DVA %u has invalid OFFSET %llu",
uint64_t offset = DVA_GET_OFFSET(dva);
uint64_t asize = DVA_GET_ASIZE(dva);
- if (BP_IS_GANG(bp))
- asize = vdev_psize_to_asize(vd, SPA_GANGBLOCKSIZE);
+ if (DVA_GET_GANG(dva))
+ asize = vdev_gang_header_asize(vd);
if (offset + asize > vd->vdev_asize)
return (B_FALSE);
*/
if (zio->io_error == ENXIO && zio->io_type == ZIO_TYPE_WRITE &&
vd != NULL && !vd->vdev_ops->vdev_op_leaf) {
+ vdev_dbgmsg(vd, "zio_vdev_io_assess(zio=%px) setting "
+ "cant_write=TRUE due to write failure with ENXIO",
+ zio);
vd->vdev_cant_write = B_TRUE;
}