lkml.org 
[lkml]   [2023]   [Feb]   [27]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    From
    Subject[PATCH v12 012/106] KVM: x86/vmx, tdx: Allow VMX, TDX to override KVM_ENABLE_CAP
    Date
    From: Isaku Yamahata <isaku.yamahata@intel.com>

    TDX has its own control of maximum number of vcpus. Not KVM_MAX_VCPUS.
    Allow vmx, tdx to override KVM_CAP_MAX_CPUS so that it can specify its own
    maximum number of cpus instead of KVM_MAX_VCPUS.

    Signed-off-by: Isaku Yamahata <isaku.yamahata@intel.com>
    ---
    arch/x86/include/asm/kvm-x86-ops.h | 1 +
    arch/x86/include/asm/kvm_host.h | 1 +
    arch/x86/kvm/vmx/main.c | 9 +++++++++
    arch/x86/kvm/vmx/tdx.c | 30 ++++++++++++++++++++++++++++++
    arch/x86/kvm/vmx/tdx.h | 3 +++
    arch/x86/kvm/vmx/x86_ops.h | 2 ++
    arch/x86/kvm/x86.c | 2 ++
    7 files changed, 48 insertions(+)

    diff --git a/arch/x86/include/asm/kvm-x86-ops.h b/arch/x86/include/asm/kvm-x86-ops.h
    index 6914f1d61803..7522c193f2b4 100644
    --- a/arch/x86/include/asm/kvm-x86-ops.h
    +++ b/arch/x86/include/asm/kvm-x86-ops.h
    @@ -22,6 +22,7 @@ KVM_X86_OP(has_emulated_msr)
    KVM_X86_OP(vcpu_after_set_cpuid)
    KVM_X86_OP(is_vm_type_supported)
    KVM_X86_OP_OPTIONAL(max_vcpus);
    +KVM_X86_OP_OPTIONAL(vm_enable_cap)
    KVM_X86_OP(vm_init)
    KVM_X86_OP_OPTIONAL(vm_destroy)
    KVM_X86_OP_OPTIONAL_RET0(vcpu_precreate)
    diff --git a/arch/x86/include/asm/kvm_host.h b/arch/x86/include/asm/kvm_host.h
    index 1c761c9e1edb..bc9ecba514a9 100644
    --- a/arch/x86/include/asm/kvm_host.h
    +++ b/arch/x86/include/asm/kvm_host.h
    @@ -1549,6 +1549,7 @@ struct kvm_x86_ops {
    bool (*is_vm_type_supported)(unsigned long vm_type);
    int (*max_vcpus)(struct kvm *kvm);
    unsigned int vm_size;
    + int (*vm_enable_cap)(struct kvm *kvm, struct kvm_enable_cap *cap);
    int (*vm_init)(struct kvm *kvm);
    void (*vm_destroy)(struct kvm *kvm);

    diff --git a/arch/x86/kvm/vmx/main.c b/arch/x86/kvm/vmx/main.c
    index 41c2e4a1b157..a090c029efd5 100644
    --- a/arch/x86/kvm/vmx/main.c
    +++ b/arch/x86/kvm/vmx/main.c
    @@ -41,6 +41,14 @@ static __init int vt_hardware_setup(void)
    return 0;
    }

    +static int vt_vm_enable_cap(struct kvm *kvm, struct kvm_enable_cap *cap)
    +{
    + if (is_td(kvm))
    + return tdx_vm_enable_cap(kvm, cap);
    +
    + return -EINVAL;
    +}
    +
    static int vt_vm_init(struct kvm *kvm)
    {
    if (is_td(kvm))
    @@ -82,6 +90,7 @@ struct kvm_x86_ops vt_x86_ops __initdata = {
    .is_vm_type_supported = vt_is_vm_type_supported,
    .max_vcpus = vt_max_vcpus,
    .vm_size = sizeof(struct kvm_vmx),
    + .vm_enable_cap = vt_vm_enable_cap,
    .vm_init = vt_vm_init,
    .vm_destroy = vmx_vm_destroy,

    diff --git a/arch/x86/kvm/vmx/tdx.c b/arch/x86/kvm/vmx/tdx.c
    index cfedb2592725..16e207168dc1 100644
    --- a/arch/x86/kvm/vmx/tdx.c
    +++ b/arch/x86/kvm/vmx/tdx.c
    @@ -16,6 +16,36 @@
    offsetof(struct tdsysinfo_struct, cpuid_configs)) \
    / sizeof(struct tdx_cpuid_config))

    +int tdx_vm_enable_cap(struct kvm *kvm, struct kvm_enable_cap *cap)
    +{
    + int r;
    +
    + switch (cap->cap) {
    + case KVM_CAP_MAX_VCPUS: {
    + if (cap->flags || cap->args[0] == 0)
    + return -EINVAL;
    + if (cap->args[0] > KVM_MAX_VCPUS)
    + return -E2BIG;
    + if (cap->args[0] > TDX_MAX_VCPUS)
    + return -E2BIG;
    +
    + mutex_lock(&kvm->lock);
    + if (kvm->created_vcpus)
    + r = -EBUSY;
    + else {
    + kvm->max_vcpus = cap->args[0];
    + r = 0;
    + }
    + mutex_unlock(&kvm->lock);
    + break;
    + }
    + default:
    + r = -EINVAL;
    + break;
    + }
    + return r;
    +}
    +
    int tdx_dev_ioctl(void __user *argp)
    {
    struct kvm_tdx_capabilities __user *user_caps;
    diff --git a/arch/x86/kvm/vmx/tdx.h b/arch/x86/kvm/vmx/tdx.h
    index 2210c8c1e893..3860aa351bd9 100644
    --- a/arch/x86/kvm/vmx/tdx.h
    +++ b/arch/x86/kvm/vmx/tdx.h
    @@ -3,6 +3,9 @@
    #define __KVM_X86_TDX_H

    #ifdef CONFIG_INTEL_TDX_HOST
    +
    +#include "tdx_ops.h"
    +
    struct kvm_tdx {
    struct kvm kvm;
    /* TDX specific members follow. */
    diff --git a/arch/x86/kvm/vmx/x86_ops.h b/arch/x86/kvm/vmx/x86_ops.h
    index 6598e16f8e9f..71f7dc9ca118 100644
    --- a/arch/x86/kvm/vmx/x86_ops.h
    +++ b/arch/x86/kvm/vmx/x86_ops.h
    @@ -142,12 +142,14 @@ int __init tdx_hardware_setup(struct kvm_x86_ops *x86_ops);
    bool tdx_is_vm_type_supported(unsigned long type);
    int tdx_dev_ioctl(void __user *argp);

    +int tdx_vm_enable_cap(struct kvm *kvm, struct kvm_enable_cap *cap);
    int tdx_vm_ioctl(struct kvm *kvm, void __user *argp);
    #else
    static inline int tdx_hardware_setup(struct kvm_x86_ops *x86_ops) { return -ENOSYS; }
    static inline bool tdx_is_vm_type_supported(unsigned long type) { return false; }
    static inline int tdx_dev_ioctl(void __user *argp) { return -EOPNOTSUPP; };

    +static inline int tdx_vm_enable_cap(struct kvm *kvm, struct kvm_enable_cap *cap) { return -EINVAL; };
    static inline int tdx_vm_ioctl(struct kvm *kvm, void __user *argp) { return -EOPNOTSUPP; }
    #endif

    diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c
    index c54baa3973f2..318e36535aa6 100644
    --- a/arch/x86/kvm/x86.c
    +++ b/arch/x86/kvm/x86.c
    @@ -6421,6 +6421,8 @@ int kvm_vm_ioctl_enable_cap(struct kvm *kvm,
    break;
    default:
    r = -EINVAL;
    + if (kvm_x86_ops.vm_enable_cap)
    + r = static_call(kvm_x86_vm_enable_cap)(kvm, cap);
    break;
    }
    return r;
    --
    2.25.1
    \
     
     \ /
      Last update: 2023-03-27 00:36    [W:4.190 / U:0.076 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site