Commit 56f289a8 authored by Sean Christopherson's avatar Sean Christopherson Committed by Paolo Bonzini

KVM: x86: Add a helper to retrieve userspace address from kvm_device_attr

Add a helper to handle converting the u64 userspace address embedded in
struct kvm_device_attr into a userspace pointer, it's all too easy to
forget the intermediate "unsigned long" cast as well as the truncation
check.

No functional change intended.
Signed-off-by: default avatarSean Christopherson <seanjc@google.com>
Signed-off-by: default avatarPaolo Bonzini <pbonzini@redhat.com>
parent dd4516ae
...@@ -4332,7 +4332,15 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext) ...@@ -4332,7 +4332,15 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext)
break; break;
} }
return r; 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(-EFAULT);
return uaddr;
} }
long kvm_arch_dev_ioctl(struct file *filp, long kvm_arch_dev_ioctl(struct file *filp,
...@@ -5025,11 +5033,11 @@ static int kvm_arch_tsc_has_attr(struct kvm_vcpu *vcpu, ...@@ -5025,11 +5033,11 @@ static int kvm_arch_tsc_has_attr(struct kvm_vcpu *vcpu,
static int kvm_arch_tsc_get_attr(struct kvm_vcpu *vcpu, static int kvm_arch_tsc_get_attr(struct kvm_vcpu *vcpu,
struct kvm_device_attr *attr) struct kvm_device_attr *attr)
{ {
u64 __user *uaddr = (u64 __user *)(unsigned long)attr->addr; u64 __user *uaddr = kvm_get_attr_addr(attr);
int r; int r;
if ((u64)(unsigned long)uaddr != attr->addr) if (IS_ERR(uaddr))
return -EFAULT; return PTR_ERR(uaddr);
switch (attr->attr) { switch (attr->attr) {
case KVM_VCPU_TSC_OFFSET: case KVM_VCPU_TSC_OFFSET:
...@@ -5048,12 +5056,12 @@ static int kvm_arch_tsc_get_attr(struct kvm_vcpu *vcpu, ...@@ -5048,12 +5056,12 @@ static int kvm_arch_tsc_get_attr(struct kvm_vcpu *vcpu,
static int kvm_arch_tsc_set_attr(struct kvm_vcpu *vcpu, static int kvm_arch_tsc_set_attr(struct kvm_vcpu *vcpu,
struct kvm_device_attr *attr) struct kvm_device_attr *attr)
{ {
u64 __user *uaddr = (u64 __user *)(unsigned long)attr->addr; u64 __user *uaddr = kvm_get_attr_addr(attr);
struct kvm *kvm = vcpu->kvm; struct kvm *kvm = vcpu->kvm;
int r; int r;
if ((u64)(unsigned long)uaddr != attr->addr) if (IS_ERR(uaddr))
return -EFAULT; return PTR_ERR(uaddr);
switch (attr->attr) { switch (attr->attr) {
case KVM_VCPU_TSC_OFFSET: { case KVM_VCPU_TSC_OFFSET: {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment