Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

paravirt: add hooks for ptep_modify_prot_start/commit

This patch adds paravirt-ops hooks in pv_mmu_ops for ptep_modify_prot_start and
ptep_modify_prot_commit. This allows the hypervisor-specific backends to
implement these in some more efficient way.

Signed-off-by: Jeremy Fitzhardinge <jeremy.fitzhardinge@citrix.com>
Acked-by: Linus Torvalds <torvalds@linux-foundation.org>
Acked-by: Hugh Dickins <hugh@veritas.com>
Signed-off-by: Ingo Molnar <mingo@elte.hu>

authored by

Jeremy Fitzhardinge and committed by
Ingo Molnar
08b882c6 1ea0704e

+34
+3
arch/x86/kernel/paravirt.c
··· 380 380 .pte_update = paravirt_nop, 381 381 .pte_update_defer = paravirt_nop, 382 382 383 + .ptep_modify_prot_start = __ptep_modify_prot_start, 384 + .ptep_modify_prot_commit = __ptep_modify_prot_commit, 385 + 383 386 #ifdef CONFIG_HIGHPTE 384 387 .kmap_atomic_pte = kmap_atomic, 385 388 #endif
+3
arch/x86/xen/enlighten.c
··· 1138 1138 .set_pte_at = xen_set_pte_at, 1139 1139 .set_pmd = xen_set_pmd_hyper, 1140 1140 1141 + .ptep_modify_prot_start = __ptep_modify_prot_start, 1142 + .ptep_modify_prot_commit = __ptep_modify_prot_commit, 1143 + 1141 1144 .pte_val = xen_pte_val, 1142 1145 .pte_flags = native_pte_val, 1143 1146 .pgd_val = xen_pgd_val,
+28
include/asm-x86/paravirt.h
··· 238 238 void (*pte_update_defer)(struct mm_struct *mm, 239 239 unsigned long addr, pte_t *ptep); 240 240 241 + pte_t (*ptep_modify_prot_start)(struct mm_struct *mm, unsigned long addr, 242 + pte_t *ptep); 243 + void (*ptep_modify_prot_commit)(struct mm_struct *mm, unsigned long addr, 244 + pte_t *ptep, pte_t pte); 245 + 241 246 pteval_t (*pte_val)(pte_t); 242 247 pteval_t (*pte_flags)(pte_t); 243 248 pte_t (*make_pte)(pteval_t pte); ··· 1042 1037 pgd.pgd); 1043 1038 1044 1039 return ret; 1040 + } 1041 + 1042 + #define __HAVE_ARCH_PTEP_MODIFY_PROT_TRANSACTION 1043 + static inline pte_t ptep_modify_prot_start(struct mm_struct *mm, unsigned long addr, 1044 + pte_t *ptep) 1045 + { 1046 + pteval_t ret; 1047 + 1048 + ret = PVOP_CALL3(pteval_t, pv_mmu_ops.ptep_modify_prot_start, 1049 + mm, addr, ptep); 1050 + 1051 + return (pte_t) { .pte = ret }; 1052 + } 1053 + 1054 + static inline void ptep_modify_prot_commit(struct mm_struct *mm, unsigned long addr, 1055 + pte_t *ptep, pte_t pte) 1056 + { 1057 + if (sizeof(pteval_t) > sizeof(long)) 1058 + /* 5 arg words */ 1059 + pv_mmu_ops.ptep_modify_prot_commit(mm, addr, ptep, pte); 1060 + else 1061 + PVOP_VCALL4(pv_mmu_ops.ptep_modify_prot_commit, 1062 + mm, addr, ptep, pte.pte); 1045 1063 } 1046 1064 1047 1065 static inline void set_pte(pte_t *ptep, pte_t pte)