Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 633a08b8 authored by Al Viro's avatar Al Viro
Browse files

[PATCH] introduce __blkdev_driver_ioctl()



Analog of blkdev_driver_ioctl() with sane arguments.  For
now uses fake struct file, by the end of the series it won't
and blkdev_driver_ioctl() will become a wrapper around it.

Signed-off-by: default avatarAl Viro <viro@zeniv.linux.org.uk>
parent a0eb62a0
Loading
Loading
Loading
Loading
+31 −0
Original line number Diff line number Diff line
@@ -283,6 +283,37 @@ int blkdev_driver_ioctl(struct inode *inode, struct file *file,
}
EXPORT_SYMBOL_GPL(blkdev_driver_ioctl);

int __blkdev_driver_ioctl(struct block_device *bdev, fmode_t mode,
			unsigned cmd, unsigned long arg)
{
	struct gendisk *disk = bdev->bd_disk;
	int ret;
	/* you bet it'll go away by the end of patch series */
	struct file fake_file = {};
	struct dentry fake_dentry = {};
	fake_file.f_mode = mode;
	fake_file.f_path.dentry = &fake_dentry;
	fake_dentry.d_inode = bdev->bd_inode;

	if (disk->fops->unlocked_ioctl)
		return disk->fops->unlocked_ioctl(&fake_file, cmd, arg);

	if (disk->fops->ioctl) {
		lock_kernel();
		ret = disk->fops->ioctl(bdev->bd_inode, &fake_file, cmd, arg);
		unlock_kernel();
		return ret;
	}

	return -ENOTTY;
}
/*
 * For the record: _GPL here is only because somebody decided to slap it
 * on the previous export.  Sheer idiocy, since it wasn't copyrightable
 * at all and could be open-coded without any exports by anybody who cares.
 */
EXPORT_SYMBOL_GPL(__blkdev_driver_ioctl);

/*
 * always keep this in sync with compat_blkdev_ioctl() and
 * compat_blkdev_locked_ioctl()
+2 −2
Original line number Diff line number Diff line
@@ -2819,8 +2819,8 @@ static int pkt_ioctl(struct inode *inode, struct file *file, unsigned int cmd, u
	case CDROM_LAST_WRITTEN:
	case CDROM_SEND_PACKET:
	case SCSI_IOCTL_SEND_COMMAND:
		return blkdev_driver_ioctl(pd->bdev->bd_inode, pd->bdev->bd_disk,
					file, cmd, arg);
		return __blkdev_driver_ioctl(pd->bdev, file ? file->f_mode : 0,
					cmd, arg);

	default:
		VPRINTK(DRIVER_NAME": Unknown ioctl for %s (%x)\n", pd->name, cmd);
+1 −9
Original line number Diff line number Diff line
@@ -114,15 +114,7 @@ static int linear_ioctl(struct dm_target *ti, unsigned int cmd,
			unsigned long arg)
{
	struct linear_c *lc = (struct linear_c *) ti->private;
	struct block_device *bdev = lc->dev->bdev;
	struct file fake_file = {};
	struct dentry fake_dentry = {};

	fake_file.f_mode = lc->dev->mode;
	fake_file.f_path.dentry = &fake_dentry;
	fake_dentry.d_inode = bdev->bd_inode;

	return blkdev_driver_ioctl(bdev->bd_inode, &fake_file, bdev->bd_disk, cmd, arg);
	return __blkdev_driver_ioctl(lc->dev->bdev, lc->dev->mode, cmd, arg);
}

static int linear_merge(struct dm_target *ti, struct bvec_merge_data *bvm,
+3 −8
Original line number Diff line number Diff line
@@ -1400,13 +1400,10 @@ static int multipath_ioctl(struct dm_target *ti, unsigned int cmd,
{
	struct multipath *m = (struct multipath *) ti->private;
	struct block_device *bdev = NULL;
	fmode_t mode = 0;
	unsigned long flags;
	struct file fake_file = {};
	struct dentry fake_dentry = {};
	int r = 0;

	fake_file.f_path.dentry = &fake_dentry;

	spin_lock_irqsave(&m->lock, flags);

	if (!m->current_pgpath)
@@ -1414,8 +1411,7 @@ static int multipath_ioctl(struct dm_target *ti, unsigned int cmd,

	if (m->current_pgpath) {
		bdev = m->current_pgpath->path.dev->bdev;
		fake_dentry.d_inode = bdev->bd_inode;
		fake_file.f_mode = m->current_pgpath->path.dev->mode;
		mode = m->current_pgpath->path.dev->mode;
	}

	if (m->queue_io)
@@ -1425,8 +1421,7 @@ static int multipath_ioctl(struct dm_target *ti, unsigned int cmd,

	spin_unlock_irqrestore(&m->lock, flags);

	return r ? : blkdev_driver_ioctl(bdev->bd_inode, &fake_file,
					 bdev->bd_disk, cmd, arg);
	return r ? : __blkdev_driver_ioctl(bdev, mode, cmd, arg);
}

/*-----------------------------------------------------------------
+2 −0
Original line number Diff line number Diff line
@@ -1074,6 +1074,8 @@ struct block_device_operations {
	struct module *owner;
};

extern int __blkdev_driver_ioctl(struct block_device *, fmode_t, unsigned int,
				 unsigned long);
#else /* CONFIG_BLOCK */
/*
 * stubs for when the block layer is configured out