Commit ba53f95c authored by xiongmengbiao's avatar xiongmengbiao
Browse files

drivers/crypto/ccp: Allow VM without a configured vid to use TKM

hygon inclusion
category: feature
bugzilla: https://gitee.com/openeuler/kernel/issues/I9C3AM


CVE: NA

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

If the guest does not explicitly specify a VID
via `vpsp_add_vid`, VID 0 will be used by default,
sharing the key space with the host.

A `vpsp_set_default_vid_permission` ioctl call
has been added to control the behavior of the default VID.
If the default VID permission is set to "not allowed,"
any guest that does not explicitly specify a VID
will be denied access to the TKM function.

Signed-off-by: default avatarxiongmengbiao <xiongmengbiao@hygon.cn>
parent 36037a92
Loading
Loading
Loading
Loading
+2 −2
Original line number Diff line number Diff line
@@ -536,9 +536,9 @@ int kvm_pv_psp_op(struct kvm *kvm, int cmd, gpa_t data_gpa, gpa_t psp_ret_gpa,

	// only tkm cmd need vid
	if (cmd_type_is_tkm(vcmd->cmd_id)) {
		// if vm without set vid, then tkm command is not allowed
		// check the permission to use the default vid when no vid is set
		ret = vpsp_get_vid(&vid, kvm->userspace_pid);
		if (ret) {
		if (ret && !vpsp_get_default_vid_permission()) {
			pr_err("[%s]: not allowed tkm command without vid\n", __func__);
			return -EFAULT;
		}
+32 −0
Original line number Diff line number Diff line
@@ -36,12 +36,16 @@ enum HYGON_PSP_OPCODE {
enum VPSP_DEV_CTRL_OPCODE {
	VPSP_OP_VID_ADD,
	VPSP_OP_VID_DEL,
	VPSP_OP_SET_DEFAULT_VID_PERMISSION,
	VPSP_OP_GET_DEFAULT_VID_PERMISSION,
};

struct vpsp_dev_ctrl {
	unsigned char op;
	union {
		unsigned int vid;
		// Set or check the permissions for the default VID
		unsigned int def_vid_perm;
		unsigned char reserved[128];
	} data;
};
@@ -175,6 +179,23 @@ static void swap_vid_entries(void *a, void *b, int size)
	memcpy(b, &entry, size);
}

/**
 * When 'allow_default_vid' is set to 1,
 * QEMU is allowed to use 'vid 0' by default
 * in the absence of a valid 'vid' setting.
 */
uint32_t allow_default_vid = 1;
void vpsp_set_default_vid_permission(uint32_t is_allow)
{
	allow_default_vid = is_allow;
}

int vpsp_get_default_vid_permission(void)
{
	return allow_default_vid;
}
EXPORT_SYMBOL_GPL(vpsp_get_default_vid_permission);

/**
 * When the virtual machine executes the 'tkm' command,
 * it needs to retrieve the corresponding 'vid'
@@ -270,6 +291,14 @@ static int do_vpsp_op_ioctl(struct vpsp_dev_ctrl *ctrl)
		ret = vpsp_del_vid();
		break;

	case VPSP_OP_SET_DEFAULT_VID_PERMISSION:
		vpsp_set_default_vid_permission(ctrl->data.def_vid_perm);
		break;

	case VPSP_OP_GET_DEFAULT_VID_PERMISSION:
		ctrl->data.def_vid_perm = vpsp_get_default_vid_permission();
		break;

	default:
		ret = -EINVAL;
		break;
@@ -318,6 +347,9 @@ static long ioctl_psp(struct file *file, unsigned int ioctl, unsigned long arg)
			sizeof(struct vpsp_dev_ctrl)))
			return -EFAULT;
		ret = do_vpsp_op_ioctl(&vpsp_ctrl_op);
		if (!ret && copy_to_user((void __user *)arg, &vpsp_ctrl_op,
				sizeof(struct vpsp_dev_ctrl)))
			return -EFAULT;
		break;

	default:
+4 −0
Original line number Diff line number Diff line
@@ -197,6 +197,7 @@ int vpsp_try_do_cmd(uint32_t vid, int cmd, void *data, struct vpsp_ret *psp_ret)

int vpsp_get_vid(uint32_t *vid, pid_t pid);

int vpsp_get_default_vid_permission(void);
#else	/* !CONFIG_CRYPTO_DEV_SP_PSP */

static inline int vpsp_do_cmd(uint32_t vid, int cmd, void *data, int *psp_ret) { return -ENODEV; }
@@ -221,6 +222,9 @@ vpsp_try_do_cmd(uint32_t vid, int cmd,

static inline int
vpsp_get_vid(uint32_t *vid, pid_t pid) { return -ENODEV; }

static inline int
vpsp_get_default_vid_permission(void) { return -ENODEV; }
#endif	/* CONFIG_CRYPTO_DEV_SP_PSP */

typedef int (*p2c_notifier_t)(uint32_t id, uint64_t data);