Loading arch/arm/kvm/mmu.c +28 −6 Original line number Diff line number Diff line Loading @@ -334,6 +334,17 @@ static int __create_hyp_mappings(pgd_t *pgdp, return err; } static phys_addr_t kvm_kaddr_to_phys(void *kaddr) { if (!is_vmalloc_addr(kaddr)) { BUG_ON(!virt_addr_valid(kaddr)); return __pa(kaddr); } else { return page_to_phys(vmalloc_to_page(kaddr)) + offset_in_page(kaddr); } } /** * create_hyp_mappings - duplicate a kernel virtual address range in Hyp mode * @from: The virtual kernel start address of the range Loading @@ -345,16 +356,27 @@ static int __create_hyp_mappings(pgd_t *pgdp, */ int create_hyp_mappings(void *from, void *to) { unsigned long phys_addr = virt_to_phys(from); phys_addr_t phys_addr; unsigned long virt_addr; unsigned long start = KERN_TO_HYP((unsigned long)from); unsigned long end = KERN_TO_HYP((unsigned long)to); /* Check for a valid kernel memory mapping */ if (!virt_addr_valid(from) || !virt_addr_valid(to - 1)) return -EINVAL; start = start & PAGE_MASK; end = PAGE_ALIGN(end); return __create_hyp_mappings(hyp_pgd, start, end, __phys_to_pfn(phys_addr), PAGE_HYP); for (virt_addr = start; virt_addr < end; virt_addr += PAGE_SIZE) { int err; phys_addr = kvm_kaddr_to_phys(from + virt_addr - start); err = __create_hyp_mappings(hyp_pgd, virt_addr, virt_addr + PAGE_SIZE, __phys_to_pfn(phys_addr), PAGE_HYP); if (err) return err; } return 0; } /** Loading Loading
arch/arm/kvm/mmu.c +28 −6 Original line number Diff line number Diff line Loading @@ -334,6 +334,17 @@ static int __create_hyp_mappings(pgd_t *pgdp, return err; } static phys_addr_t kvm_kaddr_to_phys(void *kaddr) { if (!is_vmalloc_addr(kaddr)) { BUG_ON(!virt_addr_valid(kaddr)); return __pa(kaddr); } else { return page_to_phys(vmalloc_to_page(kaddr)) + offset_in_page(kaddr); } } /** * create_hyp_mappings - duplicate a kernel virtual address range in Hyp mode * @from: The virtual kernel start address of the range Loading @@ -345,16 +356,27 @@ static int __create_hyp_mappings(pgd_t *pgdp, */ int create_hyp_mappings(void *from, void *to) { unsigned long phys_addr = virt_to_phys(from); phys_addr_t phys_addr; unsigned long virt_addr; unsigned long start = KERN_TO_HYP((unsigned long)from); unsigned long end = KERN_TO_HYP((unsigned long)to); /* Check for a valid kernel memory mapping */ if (!virt_addr_valid(from) || !virt_addr_valid(to - 1)) return -EINVAL; start = start & PAGE_MASK; end = PAGE_ALIGN(end); return __create_hyp_mappings(hyp_pgd, start, end, __phys_to_pfn(phys_addr), PAGE_HYP); for (virt_addr = start; virt_addr < end; virt_addr += PAGE_SIZE) { int err; phys_addr = kvm_kaddr_to_phys(from + virt_addr - start); err = __create_hyp_mappings(hyp_pgd, virt_addr, virt_addr + PAGE_SIZE, __phys_to_pfn(phys_addr), PAGE_HYP); if (err) return err; } return 0; } /** Loading