Commit 4eba0eab authored by jiangdongxu's avatar jiangdongxu
Browse files

vhost-vdpa: add uAPI for device buffer

virt inclusion
category: feature
bugzilla: https://gitee.com/openeuler/kernel/issues/I86ITO



----------------------------------------------------------------------

These new ioctl add support for saving/loading device status from
usersapce.

When vhost-vdpa device start migration, VMM need to call these ioctl to
save/load device status of vhost-vdpa devices if these ops is
implemented.

Signed-off-by: default avatarjiangdongxu <jiangdongxu1@huawei.com>
parent f05bc135
Loading
Loading
Loading
Loading
+71 −0
Original line number Diff line number Diff line
@@ -567,6 +567,68 @@ static long vhost_vdpa_resume(struct vhost_vdpa *v)
	return ops->resume(vdpa);
}

static int vhost_vdpa_get_dev_buffer_size(struct vhost_vdpa *v,
					  uint32_t __user *argp)
{
	struct vdpa_device *vdpa = v->vdpa;
	const struct vdpa_config_ops *ops = vdpa->config;
	uint32_t size;

	if (!ops->get_dev_buffer_size)
		return -EOPNOTSUPP;

	size = ops->get_dev_buffer_size(vdpa);

	if (copy_to_user(argp, &size, sizeof(size)))
		return -EFAULT;

	return 0;
}

static int vhost_vdpa_get_dev_buffer(struct vhost_vdpa *v,
				     struct vhost_vdpa_config __user *c)
{
	struct vdpa_device *vdpa = v->vdpa;
	const struct vdpa_config_ops *ops = vdpa->config;
	struct vhost_vdpa_config config;
	int ret;
	unsigned long size = offsetof(struct vhost_vdpa_config, buf);

	if (copy_from_user(&config, c, size))
		return -EFAULT;

	if (!ops->get_dev_buffer)
		return -EOPNOTSUPP;

	down_read(&vdpa->cf_lock);
	ret = ops->get_dev_buffer(vdpa, config.off, c->buf, config.len);
	up_read(&vdpa->cf_lock);

	return ret;
}

static int vhost_vdpa_set_dev_buffer(struct vhost_vdpa *v,
				     struct vhost_vdpa_config __user *c)
{
	struct vdpa_device *vdpa = v->vdpa;
	const struct vdpa_config_ops *ops = vdpa->config;
	struct vhost_vdpa_config config;
	int ret;
	unsigned long size = offsetof(struct vhost_vdpa_config, buf);

	if (copy_from_user(&config, c, size))
		return -EFAULT;

	if (!ops->set_dev_buffer)
		return -EOPNOTSUPP;

	down_write(&vdpa->cf_lock);
	ret = ops->set_dev_buffer(vdpa, config.off, c->buf, config.len);
	up_write(&vdpa->cf_lock);

	return ret;
}

static long vhost_vdpa_set_log_base(struct vhost_vdpa *v, u64 __user *argp)
{
	struct vdpa_device *vdpa = v->vdpa;
@@ -818,6 +880,15 @@ static long vhost_vdpa_unlocked_ioctl(struct file *filep,
	case VHOST_VDPA_RESUME:
		r = vhost_vdpa_resume(v);
		break;
	case VHOST_GET_DEV_BUFFER_SIZE:
		r = vhost_vdpa_get_dev_buffer_size(v, argp);
		break;
	case VHOST_GET_DEV_BUFFER:
		r = vhost_vdpa_get_dev_buffer(v, argp);
		break;
	case VHOST_SET_DEV_BUFFER:
		r = vhost_vdpa_set_dev_buffer(v, argp);
		break;
	default:
		r = vhost_dev_ioctl(&v->vdev, cmd, argp);
		if (r == -ENOIOCTLCMD)
+5 −0
Original line number Diff line number Diff line
@@ -192,4 +192,9 @@
 */
#define VHOST_VDPA_RESUME		_IO(VHOST_VIRTIO, 0x7E)

/* set and get device buffer */
#define VHOST_GET_DEV_BUFFER _IOR(VHOST_VIRTIO, 0xb0, struct vhost_vdpa_config)
#define VHOST_SET_DEV_BUFFER _IOW(VHOST_VIRTIO, 0xb1, struct vhost_vdpa_config)
#define VHOST_GET_DEV_BUFFER_SIZE _IOR(VHOST_VIRTIO, 0xb3, __u32)

#endif