Message ID | 20240226190344.787149-3-pbonzini@redhat.com (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
Series | KVM: SEV: allow customizing VMSA features | expand |
On Mon, Feb 26, 2024 at 02:03:31PM -0500, Paolo Bonzini wrote: > There is no danger to the kernel if userspace provides a 64-bit value that > has the high bits set, but for whatever reason happ[ens to resolve to an ^ remove the messy char. > address that has something mapped there. KVM uses the checked version > of put_user() in kvm_x86_dev_get_attr(). See from the code change, not just kvm_x86_dev_get_attr(). Thanks, Yilun > > Suggested-by: Sean Christopherson <seanjc@google.com> > Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> > --- > arch/x86/kvm/x86.c | 24 +++--------------------- > 1 file changed, 3 insertions(+), 21 deletions(-) > > diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c > index f3f7405e0628..14c969782d73 100644 > --- a/arch/x86/kvm/x86.c > +++ b/arch/x86/kvm/x86.c > @@ -4791,25 +4791,13 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext) > return r; > } > > -static inline void __user *kvm_get_attr_addr(struct kvm_device_attr *attr) > -{ > - void __user *uaddr = (void __user*)(unsigned long)attr->addr; > - > - if ((u64)(unsigned long)uaddr != attr->addr) > - return ERR_PTR_USR(-EFAULT); > - return uaddr; > -} > - > static int kvm_x86_dev_get_attr(struct kvm_device_attr *attr) > { > - u64 __user *uaddr = kvm_get_attr_addr(attr); > + u64 __user *uaddr = u64_to_user_ptr(attr->addr); > > if (attr->group) > return -ENXIO; > > - if (IS_ERR(uaddr)) > - return PTR_ERR(uaddr); > - > switch (attr->attr) { > case KVM_X86_XCOMP_GUEST_SUPP: > if (put_user(kvm_caps.supported_xcr0, uaddr)) > @@ -5664,12 +5652,9 @@ static int kvm_arch_tsc_has_attr(struct kvm_vcpu *vcpu, > static int kvm_arch_tsc_get_attr(struct kvm_vcpu *vcpu, > struct kvm_device_attr *attr) > { > - u64 __user *uaddr = kvm_get_attr_addr(attr); > + u64 __user *uaddr = u64_to_user_ptr(attr->addr); > int r; > > - if (IS_ERR(uaddr)) > - return PTR_ERR(uaddr); > - > switch (attr->attr) { > case KVM_VCPU_TSC_OFFSET: > r = -EFAULT; > @@ -5687,13 +5672,10 @@ static int kvm_arch_tsc_get_attr(struct kvm_vcpu *vcpu, > static int kvm_arch_tsc_set_attr(struct kvm_vcpu *vcpu, > struct kvm_device_attr *attr) > { > - u64 __user *uaddr = kvm_get_attr_addr(attr); > + u64 __user *uaddr = u64_to_user_ptr(attr->addr); > struct kvm *kvm = vcpu->kvm; > int r; > > - if (IS_ERR(uaddr)) > - return PTR_ERR(uaddr); > - > switch (attr->attr) { > case KVM_VCPU_TSC_OFFSET: { > u64 offset, tsc, ns; > -- > 2.39.1 > > >
diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c index f3f7405e0628..14c969782d73 100644 --- a/arch/x86/kvm/x86.c +++ b/arch/x86/kvm/x86.c @@ -4791,25 +4791,13 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext) return r; } -static inline void __user *kvm_get_attr_addr(struct kvm_device_attr *attr) -{ - void __user *uaddr = (void __user*)(unsigned long)attr->addr; - - if ((u64)(unsigned long)uaddr != attr->addr) - return ERR_PTR_USR(-EFAULT); - return uaddr; -} - static int kvm_x86_dev_get_attr(struct kvm_device_attr *attr) { - u64 __user *uaddr = kvm_get_attr_addr(attr); + u64 __user *uaddr = u64_to_user_ptr(attr->addr); if (attr->group) return -ENXIO; - if (IS_ERR(uaddr)) - return PTR_ERR(uaddr); - switch (attr->attr) { case KVM_X86_XCOMP_GUEST_SUPP: if (put_user(kvm_caps.supported_xcr0, uaddr)) @@ -5664,12 +5652,9 @@ static int kvm_arch_tsc_has_attr(struct kvm_vcpu *vcpu, static int kvm_arch_tsc_get_attr(struct kvm_vcpu *vcpu, struct kvm_device_attr *attr) { - u64 __user *uaddr = kvm_get_attr_addr(attr); + u64 __user *uaddr = u64_to_user_ptr(attr->addr); int r; - if (IS_ERR(uaddr)) - return PTR_ERR(uaddr); - switch (attr->attr) { case KVM_VCPU_TSC_OFFSET: r = -EFAULT; @@ -5687,13 +5672,10 @@ static int kvm_arch_tsc_get_attr(struct kvm_vcpu *vcpu, static int kvm_arch_tsc_set_attr(struct kvm_vcpu *vcpu, struct kvm_device_attr *attr) { - u64 __user *uaddr = kvm_get_attr_addr(attr); + u64 __user *uaddr = u64_to_user_ptr(attr->addr); struct kvm *kvm = vcpu->kvm; int r; - if (IS_ERR(uaddr)) - return PTR_ERR(uaddr); - switch (attr->attr) { case KVM_VCPU_TSC_OFFSET: { u64 offset, tsc, ns;
There is no danger to the kernel if userspace provides a 64-bit value that has the high bits set, but for whatever reason happ[ens to resolve to an address that has something mapped there. KVM uses the checked version of put_user() in kvm_x86_dev_get_attr(). Suggested-by: Sean Christopherson <seanjc@google.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> --- arch/x86/kvm/x86.c | 24 +++--------------------- 1 file changed, 3 insertions(+), 21 deletions(-)