Creates the patchfile which corrects a (memory) bug of the paravirtualization feature in kernel 2.6.25 (which got corrected later in 2.6.29) (File 998-paravirt_release_pmd.patch, which I send as standalone in 2/2)
Signed-off-by: Alexander Stadler <sa.maillists at univie.ac.at> ------ diff -urN a/8.09/target/linux/generic-2.6/patches-2.6.25/998-paravirt_release_pmd.patch b/8.09/target/linux/generic-2.6/patches-2.6.25/998-paravirt_release_pmd.patch --- a/8.09/target/linux/generic-2.6/patches-2.6.25/998-paravirt_release_pmd.patch 1970-01-01 01:00:00.000000000 +0100 +++ b/8.09/target/linux/generic-2.6/patches-2.6.25/998-paravirt_release_pmd.patch 2009-04-03 15:10:30.000000000 +0200 @@ -0,0 +1,107 @@ +diff -urN openwrt-8.09/arch/x86/xen/enlighten.c openwrt/arch/x86/xen/enlighten.c +--- a/arch/x86/xen/enlighten.c 2008-09-08 12:20:51.000000000 +0200 ++++ b/arch/x86/xen/enlighten.c 2009-04-03 14:27:56.000000000 +0200 +@@ -1059,6 +1059,8 @@ + .pte_update = paravirt_nop, + .pte_update_defer = paravirt_nop, + ++ .pgd_free = paravirt_nop, ++ + .alloc_pt = xen_alloc_pt_init, + .release_pt = xen_release_pt_init, + .alloc_pd = xen_alloc_pt_init, +diff -urN openwrt-8.09/arch/x86/kernel/paravirt.c openwrt/arch/x86/kernel/paravirt.c +--- a/arch/x86/kernel/paravirt.c 2008-09-08 12:20:51.000000000 +0200 ++++ b/arch/x86/kernel/paravirt.c 2009-04-03 14:27:56.000000000 +0200 +@@ -382,6 +382,8 @@ + .flush_tlb_single = native_flush_tlb_single, + .flush_tlb_others = native_flush_tlb_others, + ++ .pgd_free = paravirt_nop, ++ + .alloc_pt = paravirt_nop, + .alloc_pd = paravirt_nop, + .alloc_pd_clone = paravirt_nop, +diff -urN openwrt-8.09/include/asm-x86/paravirt.h openwrt/include/asm-x86/paravirt.h +--- a/include/asm-x86/paravirt.h 2008-09-08 12:20:51.000000000 +0200 ++++ b/include/asm-x86/paravirt.h 2009-04-03 14:27:56.000000000 +0200 +@@ -219,6 +219,9 @@ + void (*flush_tlb_others)(const cpumask_t *cpus, struct mm_struct *mm, + unsigned long va); + ++ /* Hook for freeing a pagetable top-level */ ++ void (*pgd_free) (struct mm_struct *mm, pgd_t *pgd); ++ + /* Hooks for allocating/releasing pagetable pages */ + void (*alloc_pt)(struct mm_struct *mm, u32 pfn); + void (*alloc_pd)(struct mm_struct *mm, u32 pfn); +@@ -894,6 +897,11 @@ + PVOP_VCALL3(pv_mmu_ops.flush_tlb_others, &cpumask, mm, va); + } + ++static inline void paravirt_pgd_free(struct mm_struct *mm, pgd_t *pgd) ++{ ++ PVOP_VCALL2(pv_mmu_ops.pgd_free, mm, pgd); ++} ++ + static inline void paravirt_alloc_pt(struct mm_struct *mm, unsigned pfn) + { + PVOP_VCALL2(pv_mmu_ops.alloc_pt, mm, pfn); +diff -urN openwrt-8.09/include/asm-x86/pgalloc_32.h openwrt/include/asm-x86/pgalloc_32.h +--- a/include/asm-x86/pgalloc_32.h 2008-09-08 12:20:51.000000000 +0200 ++++ b/include/asm-x86/pgalloc_32.h 2009-04-03 14:27:56.000000000 +0200 +@@ -13,6 +13,7 @@ + #define paravirt_alloc_pt(mm, pfn) do { } while (0) + #define paravirt_alloc_pd(mm, pfn) do { } while (0) + #define paravirt_alloc_pd_clone(pfn, clonepfn, start, count) do { } while (0) ++#define paravirt_pgd_free(mm, pgd) do { } while (0) + #define paravirt_release_pt(pfn) do { } while (0) + #define paravirt_release_pd(pfn) do { } while (0) + #endif +diff -urN openwrt-8.09/arch/x86/mm/pgtable_32.c openwrt/arch/x86/mm/pgtable_32.c +--- a/arch/x86/mm/pgtable_32.c 2008-09-08 12:20:51.000000000 +0200 ++++ b/arch/x86/mm/pgtable_32.c 2009-04-03 14:27:56.000000000 +0200 +@@ -351,6 +351,7 @@ + + if (pgd && !pgd_prepopulate_pmd(mm, pgd)) { + pgd_dtor(pgd); ++ paravirt_pgd_free(mm, pgd); + free_page((unsigned long)pgd); + pgd = NULL; + } +@@ -362,6 +363,7 @@ + { + pgd_mop_up_pmds(mm, pgd); + pgd_dtor(pgd); ++ paravirt_pgd_free(mm, pgd); + free_page((unsigned long)pgd); + } + +diff -urN openwrt-8.09/arch/x86/kernel/vmi_32.c openwrt/arch/x86/kernel/vmi_32.c +--- a/arch/x86/kernel/vmi_32.c 2008-09-08 12:20:51.000000000 +0200 ++++ b/arch/x86/kernel/vmi_32.c 2009-04-03 14:27:56.000000000 +0200 +@@ -428,6 +428,16 @@ + vmi_set_page_type(pfn, VMI_PAGE_NORMAL); + } + ++/* ++ * We use the pgd_free hook for releasing the pgd page: ++ */ ++static void vmi_pgd_free(struct mm_struct *mm, pgd_t *pgd) ++{ ++ unsigned long pfn = __pa(pgd) >> PAGE_SHIFT; ++ ++ vmi_ops.release_page(pfn, VMI_PAGE_L2); ++} ++ + /* + * Helper macros for MMU update flags. We can defer updates until a flush + * or page invalidation only if the update is to the current address space +@@ -880,6 +890,7 @@ + if (vmi_ops.release_page) { + pv_mmu_ops.release_pt = vmi_release_pt; + pv_mmu_ops.release_pd = vmi_release_pd; ++ pv_mmu_ops.pgd_free = vmi_pgd_free; + } + + /* Set linear is needed in all cases */ _______________________________________________ openwrt-devel mailing list openwrt-devel@lists.openwrt.org https://lists.openwrt.org/mailman/listinfo/openwrt-devel