diff options
Diffstat (limited to 'arch/i386/xen/mmu.c')
-rw-r--r-- | arch/i386/xen/mmu.c | 52 |
1 files changed, 39 insertions, 13 deletions
diff --git a/arch/i386/xen/mmu.c b/arch/i386/xen/mmu.c index f431cf14e644..4ae038aa6c24 100644 --- a/arch/i386/xen/mmu.c +++ b/arch/i386/xen/mmu.c | |||
@@ -98,12 +98,20 @@ void make_lowmem_page_readwrite(void *vaddr) | |||
98 | 98 | ||
99 | void xen_set_pmd(pmd_t *ptr, pmd_t val) | 99 | void xen_set_pmd(pmd_t *ptr, pmd_t val) |
100 | { | 100 | { |
101 | struct mmu_update u; | 101 | struct multicall_space mcs; |
102 | struct mmu_update *u; | ||
102 | 103 | ||
103 | u.ptr = virt_to_machine(ptr).maddr; | 104 | preempt_disable(); |
104 | u.val = pmd_val_ma(val); | 105 | |
105 | if (HYPERVISOR_mmu_update(&u, 1, NULL, DOMID_SELF) < 0) | 106 | mcs = xen_mc_entry(sizeof(*u)); |
106 | BUG(); | 107 | u = mcs.args; |
108 | u->ptr = virt_to_machine(ptr).maddr; | ||
109 | u->val = pmd_val_ma(val); | ||
110 | MULTI_mmu_update(mcs.mc, u, 1, NULL, DOMID_SELF); | ||
111 | |||
112 | xen_mc_issue(PARAVIRT_LAZY_MMU); | ||
113 | |||
114 | preempt_enable(); | ||
107 | } | 115 | } |
108 | 116 | ||
109 | /* | 117 | /* |
@@ -146,20 +154,38 @@ void set_pte_mfn(unsigned long vaddr, unsigned long mfn, pgprot_t flags) | |||
146 | void xen_set_pte_at(struct mm_struct *mm, unsigned long addr, | 154 | void xen_set_pte_at(struct mm_struct *mm, unsigned long addr, |
147 | pte_t *ptep, pte_t pteval) | 155 | pte_t *ptep, pte_t pteval) |
148 | { | 156 | { |
149 | if ((mm != current->mm && mm != &init_mm) || | 157 | if (mm == current->mm || mm == &init_mm) { |
150 | HYPERVISOR_update_va_mapping(addr, pteval, 0) != 0) | 158 | if (xen_get_lazy_mode() == PARAVIRT_LAZY_MMU) { |
151 | xen_set_pte(ptep, pteval); | 159 | struct multicall_space mcs; |
160 | mcs = xen_mc_entry(0); | ||
161 | |||
162 | MULTI_update_va_mapping(mcs.mc, addr, pteval, 0); | ||
163 | xen_mc_issue(PARAVIRT_LAZY_MMU); | ||
164 | return; | ||
165 | } else | ||
166 | if (HYPERVISOR_update_va_mapping(addr, pteval, 0) == 0) | ||
167 | return; | ||
168 | } | ||
169 | xen_set_pte(ptep, pteval); | ||
152 | } | 170 | } |
153 | 171 | ||
154 | #ifdef CONFIG_X86_PAE | 172 | #ifdef CONFIG_X86_PAE |
155 | void xen_set_pud(pud_t *ptr, pud_t val) | 173 | void xen_set_pud(pud_t *ptr, pud_t val) |
156 | { | 174 | { |
157 | struct mmu_update u; | 175 | struct multicall_space mcs; |
176 | struct mmu_update *u; | ||
158 | 177 | ||
159 | u.ptr = virt_to_machine(ptr).maddr; | 178 | preempt_disable(); |
160 | u.val = pud_val_ma(val); | 179 | |
161 | if (HYPERVISOR_mmu_update(&u, 1, NULL, DOMID_SELF) < 0) | 180 | mcs = xen_mc_entry(sizeof(*u)); |
162 | BUG(); | 181 | u = mcs.args; |
182 | u->ptr = virt_to_machine(ptr).maddr; | ||
183 | u->val = pud_val_ma(val); | ||
184 | MULTI_mmu_update(mcs.mc, u, 1, NULL, DOMID_SELF); | ||
185 | |||
186 | xen_mc_issue(PARAVIRT_LAZY_MMU); | ||
187 | |||
188 | preempt_enable(); | ||
163 | } | 189 | } |
164 | 190 | ||
165 | void xen_set_pte(pte_t *ptep, pte_t pte) | 191 | void xen_set_pte(pte_t *ptep, pte_t pte) |