Commit dba7688f authored by Christoph Hellwig's avatar Christoph Hellwig Committed by Martin K. Petersen
Browse files

scsi: st: Simplify ioctl handling

Merge st_ioctl_common() into st_ioctl() and streamline the invocation of
the common ioctl helpers.

Link: https://lore.kernel.org/r/20210724072033.1284840-8-hch@lst.de


Signed-off-by: default avatarChristoph Hellwig <hch@lst.de>
Signed-off-by: default avatarMartin K. Petersen <martin.petersen@oracle.com>
parent 6fade450
Loading
Loading
Loading
Loading
+29 −49
Original line number Original line Diff line number Diff line
@@ -3499,8 +3499,9 @@ static int partition_tape(struct scsi_tape *STp, int size)




/* The ioctl command */
/* The ioctl command */
static long st_ioctl_common(struct file *file, unsigned int cmd_in, void __user *p)
static long st_ioctl(struct file *file, unsigned int cmd_in, unsigned long arg)
{
{
	void __user *p = (void __user *)arg;
	int i, cmd_nr, cmd_type, bt;
	int i, cmd_nr, cmd_type, bt;
	int retval = 0;
	int retval = 0;
	unsigned int blk;
	unsigned int blk;
@@ -3820,73 +3821,52 @@ static long st_ioctl_common(struct file *file, unsigned int cmd_in, void __user
		goto out;
		goto out;
	}
	}
	mutex_unlock(&STp->lock);
	mutex_unlock(&STp->lock);
	switch (cmd_in) {
		case SCSI_IOCTL_STOP_UNIT:
			/* unload */
			retval = scsi_ioctl(STp->device, cmd_in, p);
			if (!retval) {
				STp->rew_at_close = 0;
				STp->ready = ST_NO_TAPE;
			}
			return retval;


	switch (cmd_in) {
	case SCSI_IOCTL_GET_IDLUN:
	case SCSI_IOCTL_GET_IDLUN:
	case SCSI_IOCTL_GET_BUS_NUMBER:
	case SCSI_IOCTL_GET_BUS_NUMBER:
		break;
		break;

	case SG_IO:
	case SCSI_IOCTL_SEND_COMMAND:
	case CDROM_SEND_PACKET:
		if (!capable(CAP_SYS_RAWIO))
			return -EPERM;
		fallthrough;
	default:
	default:
			if ((cmd_in == SG_IO ||
		retval = scsi_cmd_ioctl(STp->disk->queue, STp->disk,
			     cmd_in == SCSI_IOCTL_SEND_COMMAND ||
			     cmd_in == CDROM_SEND_PACKET) &&
			    !capable(CAP_SYS_RAWIO))
				i = -EPERM;
			else
				i = scsi_cmd_ioctl(STp->disk->queue, STp->disk,
					file->f_mode, cmd_in, p);
					file->f_mode, cmd_in, p);
			if (i != -ENOTTY)
		if (retval != -ENOTTY)
				return i;
			return retval;
		break;
		break;
	}
	}
	return -ENOTTY;

	retval = scsi_ioctl(STp->device, cmd_in, p);
	if (!retval && cmd_in == SCSI_IOCTL_STOP_UNIT) {
		/* unload */
		STp->rew_at_close = 0;
		STp->ready = ST_NO_TAPE;
	}
	return retval;


 out:
 out:
	mutex_unlock(&STp->lock);
	mutex_unlock(&STp->lock);
	return retval;
	return retval;
}
}


static long st_ioctl(struct file *file, unsigned int cmd_in, unsigned long arg)
{
	void __user *p = (void __user *)arg;
	struct scsi_tape *STp = file->private_data;
	int ret;

	ret = st_ioctl_common(file, cmd_in, p);
	if (ret != -ENOTTY)
		return ret;

	return scsi_ioctl(STp->device, cmd_in, p);
}

#ifdef CONFIG_COMPAT
#ifdef CONFIG_COMPAT
static long st_compat_ioctl(struct file *file, unsigned int cmd_in, unsigned long arg)
static long st_compat_ioctl(struct file *file, unsigned int cmd_in, unsigned long arg)
{
{
	void __user *p = compat_ptr(arg);
	struct scsi_tape *STp = file->private_data;
	int ret;

	/* argument conversion is handled using put_user_mtpos/put_user_mtget */
	/* argument conversion is handled using put_user_mtpos/put_user_mtget */
	switch (cmd_in) {
	switch (cmd_in) {
	case MTIOCPOS32:
	case MTIOCPOS32:
		return st_ioctl_common(file, MTIOCPOS, p);
		cmd_in = MTIOCPOS;
		break;
	case MTIOCGET32:
	case MTIOCGET32:
		return st_ioctl_common(file, MTIOCGET, p);
		cmd_in = MTIOCGET;
		break;
	}
	}


	ret = st_ioctl_common(file, cmd_in, p);
	return st_ioctl(file, cmd_in, arg);
	if (ret != -ENOTTY)
		return ret;

	return scsi_ioctl(STp->device, cmd_in, p);
}
}
#endif
#endif