Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 222919
b: refs/heads/master
c: 805e3f4
h: refs/heads/master
i:
  222917: 9f4c1e5
  222915: 01001dd
  222911: 57de753
v: v3
  • Loading branch information
Ian Campbell authored and Jeremy Fitzhardinge committed Nov 30, 2010
1 parent 68b051e commit 68f03d5
Show file tree
Hide file tree
Showing 3 changed files with 57 additions and 16 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 31e323cca9d5c8afd372976c35a5d46192f540d1
refs/heads/master: 805e3f495057aa5307ad4e3d6dc7073d4733c691
2 changes: 0 additions & 2 deletions trunk/arch/x86/xen/enlighten.c
Original file line number Diff line number Diff line change
Expand Up @@ -1187,8 +1187,6 @@ asmlinkage void __init xen_start_kernel(void)
/* Allocate and initialize top and mid mfn levels for p2m structure */
xen_build_mfn_list_list();

init_mm.pgd = pgd;

/* keep using Xen gdt for now; no urgent need to change it */

#ifdef CONFIG_X86_32
Expand Down
69 changes: 56 additions & 13 deletions trunk/arch/x86/xen/mmu.c
Original file line number Diff line number Diff line change
Expand Up @@ -2119,44 +2119,83 @@ __init pgd_t *xen_setup_kernel_pagetable(pgd_t *pgd,
return pgd;
}
#else /* !CONFIG_X86_64 */
static RESERVE_BRK_ARRAY(pmd_t, level2_kernel_pgt, PTRS_PER_PMD);
static RESERVE_BRK_ARRAY(pmd_t, initial_kernel_pmd, PTRS_PER_PMD);
static RESERVE_BRK_ARRAY(pmd_t, swapper_kernel_pmd, PTRS_PER_PMD);

static __init void xen_write_cr3_init(unsigned long cr3)
{
unsigned long pfn = PFN_DOWN(__pa(swapper_pg_dir));

BUG_ON(read_cr3() != __pa(initial_page_table));
BUG_ON(cr3 != __pa(swapper_pg_dir));

/*
* We are switching to swapper_pg_dir for the first time (from
* initial_page_table) and therefore need to mark that page
* read-only and then pin it.
*
* Xen disallows sharing of kernel PMDs for PAE
* guests. Therefore we must copy the kernel PMD from
* initial_page_table into a new kernel PMD to be used in
* swapper_pg_dir.
*/
swapper_kernel_pmd =
extend_brk(sizeof(pmd_t) * PTRS_PER_PMD, PAGE_SIZE);
memcpy(swapper_kernel_pmd, initial_kernel_pmd,
sizeof(pmd_t) * PTRS_PER_PMD);
swapper_pg_dir[KERNEL_PGD_BOUNDARY] =
__pgd(__pa(swapper_kernel_pmd) | _PAGE_PRESENT);
set_page_prot(swapper_kernel_pmd, PAGE_KERNEL_RO);

set_page_prot(swapper_pg_dir, PAGE_KERNEL_RO);
xen_write_cr3(cr3);
pin_pagetable_pfn(MMUEXT_PIN_L3_TABLE, pfn);

pin_pagetable_pfn(MMUEXT_UNPIN_TABLE,
PFN_DOWN(__pa(initial_page_table)));
set_page_prot(initial_page_table, PAGE_KERNEL);
set_page_prot(initial_kernel_pmd, PAGE_KERNEL);

pv_mmu_ops.write_cr3 = &xen_write_cr3;
}

__init pgd_t *xen_setup_kernel_pagetable(pgd_t *pgd,
unsigned long max_pfn)
{
pmd_t *kernel_pmd;

level2_kernel_pgt = extend_brk(sizeof(pmd_t) * PTRS_PER_PMD, PAGE_SIZE);
initial_kernel_pmd =
extend_brk(sizeof(pmd_t) * PTRS_PER_PMD, PAGE_SIZE);

max_pfn_mapped = PFN_DOWN(__pa(xen_start_info->pt_base) +
xen_start_info->nr_pt_frames * PAGE_SIZE +
512*1024);

kernel_pmd = m2v(pgd[KERNEL_PGD_BOUNDARY].pgd);
memcpy(level2_kernel_pgt, kernel_pmd, sizeof(pmd_t) * PTRS_PER_PMD);
memcpy(initial_kernel_pmd, kernel_pmd, sizeof(pmd_t) * PTRS_PER_PMD);

xen_map_identity_early(level2_kernel_pgt, max_pfn);
xen_map_identity_early(initial_kernel_pmd, max_pfn);

memcpy(swapper_pg_dir, pgd, sizeof(pgd_t) * PTRS_PER_PGD);
set_pgd(&swapper_pg_dir[KERNEL_PGD_BOUNDARY],
__pgd(__pa(level2_kernel_pgt) | _PAGE_PRESENT));
memcpy(initial_page_table, pgd, sizeof(pgd_t) * PTRS_PER_PGD);
initial_page_table[KERNEL_PGD_BOUNDARY] =
__pgd(__pa(initial_kernel_pmd) | _PAGE_PRESENT);

set_page_prot(level2_kernel_pgt, PAGE_KERNEL_RO);
set_page_prot(swapper_pg_dir, PAGE_KERNEL_RO);
set_page_prot(initial_kernel_pmd, PAGE_KERNEL_RO);
set_page_prot(initial_page_table, PAGE_KERNEL_RO);
set_page_prot(empty_zero_page, PAGE_KERNEL_RO);

pin_pagetable_pfn(MMUEXT_UNPIN_TABLE, PFN_DOWN(__pa(pgd)));

xen_write_cr3(__pa(swapper_pg_dir));

pin_pagetable_pfn(MMUEXT_PIN_L3_TABLE, PFN_DOWN(__pa(swapper_pg_dir)));
pin_pagetable_pfn(MMUEXT_PIN_L3_TABLE,
PFN_DOWN(__pa(initial_page_table)));
xen_write_cr3(__pa(initial_page_table));

memblock_x86_reserve_range(__pa(xen_start_info->pt_base),
__pa(xen_start_info->pt_base +
xen_start_info->nr_pt_frames * PAGE_SIZE),
"XEN PAGETABLES");

return swapper_pg_dir;
return initial_page_table;
}
#endif /* CONFIG_X86_64 */

Expand Down Expand Up @@ -2290,7 +2329,11 @@ static const struct pv_mmu_ops xen_mmu_ops __initdata = {
.write_cr2 = xen_write_cr2,

.read_cr3 = xen_read_cr3,
#ifdef CONFIG_X86_32
.write_cr3 = xen_write_cr3_init,
#else
.write_cr3 = xen_write_cr3,
#endif

.flush_tlb_user = xen_flush_tlb,
.flush_tlb_kernel = xen_flush_tlb,
Expand Down

0 comments on commit 68f03d5

Please sign in to comment.