int buf_wait ( struct buf * bp ) { LIST *pBufHead = &bp->b_vp->v_mount->mnt_buflist; /* Make sure I/O is complete */ if ((bp->b_flags & B_DONE) == 0) { if (bio_wait (bp->b_bio)) { bp->b_flags |= B_ERROR; } buf_done (bp, OK); } if ((bp->b_flags & B_ERROR) || bp->b_error) { if ((bp->b_flags & B_INVAL) == 0) { bp->b_flags |= B_INVAL; listRemove (pBufHead, &bp->b_node); /* Remove from list */ listInsert (pBufHead, NULL, &bp->b_node); /* Insert at list head */ } if (!bp->b_error) { bp->b_error = EIO; } else { bp->b_flags |= B_ERROR; } return (bp->b_error); } else { return (OK); } }
static int vdev_disk_physio(struct device *dev, caddr_t data, size_t size, uint64_t offset, int write) { struct bio *bio; int ret; bio = alloc_bio(); if (write) bio->bio_cmd = BIO_WRITE; else bio->bio_cmd = BIO_READ; bio->bio_dev = dev; bio->bio_data = data; bio->bio_offset = offset; bio->bio_bcount = size; bio->bio_dev->driver->devops->strategy(bio); ret = bio_wait(bio); destroy_bio(bio); return ret; }