ia64/xen-unstable

changeset 12567:d9f2de16ae5a

[HVM] Fix hvm_copy_[to|from]_guest_virt
which would fail if it crossed a page boundary where the guest physical
pages were not contiguous.
Signed-off-by: Tim Deegan <Tim.Deegan@xensource.com>
author Tim Deegan <Tim.Deegan@xensource.com>
date Fri Nov 24 09:42:40 2006 +0000 (2006-11-24)
parents 6d892ea6194d
children a1441f389dc1
files xen/arch/x86/hvm/hvm.c
line diff
     1.1 --- a/xen/arch/x86/hvm/hvm.c	Thu Nov 23 18:01:40 2006 +0000
     1.2 +++ b/xen/arch/x86/hvm/hvm.c	Fri Nov 24 09:42:40 2006 +0000
     1.3 @@ -330,12 +330,13 @@ void hvm_hlt(unsigned long rflags)
     1.4  /*
     1.5   * __hvm_copy():
     1.6   *  @buf  = hypervisor buffer
     1.7 - *  @addr = guest physical address to copy to/from
     1.8 + *  @addr = guest address to copy to/from
     1.9   *  @size = number of bytes to copy
    1.10   *  @dir  = copy *to* guest (TRUE) or *from* guest (FALSE)?
    1.11 + *  @virt = addr is *virtual* (TRUE) or *guest physical* (FALSE)?
    1.12   * Returns number of bytes failed to copy (0 == complete success).
    1.13   */
    1.14 -static int __hvm_copy(void *buf, paddr_t addr, int size, int dir)
    1.15 +static int __hvm_copy(void *buf, paddr_t addr, int size, int dir, int virt)
    1.16  {
    1.17      unsigned long mfn;
    1.18      char *p;
    1.19 @@ -346,7 +347,11 @@ static int __hvm_copy(void *buf, paddr_t
    1.20      {
    1.21          count = min_t(int, PAGE_SIZE - (addr & ~PAGE_MASK), todo);
    1.22  
    1.23 -        mfn = get_mfn_from_gpfn(addr >> PAGE_SHIFT);
    1.24 +        if ( virt )
    1.25 +            mfn = get_mfn_from_gpfn(shadow_gva_to_gfn(current, addr));
    1.26 +        else
    1.27 +            mfn = get_mfn_from_gpfn(addr >> PAGE_SHIFT);
    1.28 +
    1.29          if ( mfn == INVALID_MFN )
    1.30              return todo;
    1.31  
    1.32 @@ -369,24 +374,25 @@ static int __hvm_copy(void *buf, paddr_t
    1.33  
    1.34  int hvm_copy_to_guest_phys(paddr_t paddr, void *buf, int size)
    1.35  {
    1.36 -    return __hvm_copy(buf, paddr, size, 1);
    1.37 +    return __hvm_copy(buf, paddr, size, 1, 0);
    1.38  }
    1.39  
    1.40  int hvm_copy_from_guest_phys(void *buf, paddr_t paddr, int size)
    1.41  {
    1.42 -    return __hvm_copy(buf, paddr, size, 0);
    1.43 +    return __hvm_copy(buf, paddr, size, 0, 0);
    1.44  }
    1.45  
    1.46  int hvm_copy_to_guest_virt(unsigned long vaddr, void *buf, int size)
    1.47  {
    1.48 -    return __hvm_copy(buf, shadow_gva_to_gpa(current, vaddr), size, 1);
    1.49 +    return __hvm_copy(buf, vaddr, size, 1, 1);
    1.50  }
    1.51  
    1.52  int hvm_copy_from_guest_virt(void *buf, unsigned long vaddr, int size)
    1.53  {
    1.54 -    return __hvm_copy(buf, shadow_gva_to_gpa(current, vaddr), size, 0);
    1.55 +    return __hvm_copy(buf, vaddr, size, 0, 1);
    1.56  }
    1.57  
    1.58 +
    1.59  /* HVM specific printbuf. Mostly used for hvmloader chit-chat. */
    1.60  void hvm_print_line(struct vcpu *v, const char c)
    1.61  {