Ejemplo n.º 1
0
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;
}
Ejemplo n.º 2
0
static void vdev_disk_bio_done(struct bio *bio)
{
	zio_t *zio = bio->bio_caller1;

	if (bio->bio_flags & BIO_ERROR)
		zio->io_error = EIO;
	else
		zio->io_error = 0;

	destroy_bio(bio);

	zio_interrupt(zio);
}
Ejemplo n.º 3
0
static void multiplex_bio_done(struct bio *b)
{
	struct bio *bio = b->bio_caller1;
	bool error = b->bio_flags & BIO_ERROR;
	destroy_bio(b);


	// If there is an error, we store it in the original bio flags.
	// This path gets slower because then we need to end up taking the
	// bio_mutex twice. But that should be fine.
	if (error) {
		pthread_mutex_lock(&bio->bio_mutex);
		bio->bio_flags |= BIO_ERROR;
		pthread_mutex_lock(&bio->bio_mutex);
	}

	// Last one releases it. We set the biodone to always be "ok", because
	// if an error exists, we have already set that in the previous operation
	if (refcount_release(&bio->bio_refcnt))
		biodone(bio, true);
}