diff options
44 files changed, 193 insertions, 161 deletions
diff --git a/arch/alpha/include/asm/tlb.h b/arch/alpha/include/asm/tlb.h index c13636575fba..42866759f3fa 100644 --- a/arch/alpha/include/asm/tlb.h +++ b/arch/alpha/include/asm/tlb.h | |||
| @@ -9,7 +9,7 @@ | |||
| 9 | 9 | ||
| 10 | #include <asm-generic/tlb.h> | 10 | #include <asm-generic/tlb.h> |
| 11 | 11 | ||
| 12 | #define __pte_free_tlb(tlb, pte) pte_free((tlb)->mm, pte) | 12 | #define __pte_free_tlb(tlb, pte, address) pte_free((tlb)->mm, pte) |
| 13 | #define __pmd_free_tlb(tlb, pmd) pmd_free((tlb)->mm, pmd) | 13 | #define __pmd_free_tlb(tlb, pmd, address) pmd_free((tlb)->mm, pmd) |
| 14 | 14 | ||
| 15 | #endif | 15 | #endif |
diff --git a/arch/arm/include/asm/tlb.h b/arch/arm/include/asm/tlb.h index 321c83e43a1e..f41a6f57cd12 100644 --- a/arch/arm/include/asm/tlb.h +++ b/arch/arm/include/asm/tlb.h | |||
| @@ -102,8 +102,8 @@ tlb_end_vma(struct mmu_gather *tlb, struct vm_area_struct *vma) | |||
| 102 | } | 102 | } |
| 103 | 103 | ||
| 104 | #define tlb_remove_page(tlb,page) free_page_and_swap_cache(page) | 104 | #define tlb_remove_page(tlb,page) free_page_and_swap_cache(page) |
| 105 | #define pte_free_tlb(tlb, ptep) pte_free((tlb)->mm, ptep) | 105 | #define pte_free_tlb(tlb, ptep, addr) pte_free((tlb)->mm, ptep) |
| 106 | #define pmd_free_tlb(tlb, pmdp) pmd_free((tlb)->mm, pmdp) | 106 | #define pmd_free_tlb(tlb, pmdp, addr) pmd_free((tlb)->mm, pmdp) |
| 107 | 107 | ||
| 108 | #define tlb_migrate_finish(mm) do { } while (0) | 108 | #define tlb_migrate_finish(mm) do { } while (0) |
| 109 | 109 | ||
diff --git a/arch/avr32/include/asm/pgalloc.h b/arch/avr32/include/asm/pgalloc.h index 640821323943..92ecd8446ef8 100644 --- a/arch/avr32/include/asm/pgalloc.h +++ b/arch/avr32/include/asm/pgalloc.h | |||
| @@ -83,7 +83,7 @@ static inline void pte_free(struct mm_struct *mm, pgtable_t pte) | |||
| 83 | quicklist_free_page(QUICK_PT, NULL, pte); | 83 | quicklist_free_page(QUICK_PT, NULL, pte); |
| 84 | } | 84 | } |
| 85 | 85 | ||
| 86 | #define __pte_free_tlb(tlb,pte) \ | 86 | #define __pte_free_tlb(tlb,pte,addr) \ |
| 87 | do { \ | 87 | do { \ |
| 88 | pgtable_page_dtor(pte); \ | 88 | pgtable_page_dtor(pte); \ |
| 89 | tlb_remove_page((tlb), pte); \ | 89 | tlb_remove_page((tlb), pte); \ |
diff --git a/arch/cris/include/asm/pgalloc.h b/arch/cris/include/asm/pgalloc.h index a1ba761d0573..6da975db112f 100644 --- a/arch/cris/include/asm/pgalloc.h +++ b/arch/cris/include/asm/pgalloc.h | |||
| @@ -47,7 +47,7 @@ static inline void pte_free(struct mm_struct *mm, pgtable_t pte) | |||
| 47 | __free_page(pte); | 47 | __free_page(pte); |
| 48 | } | 48 | } |
| 49 | 49 | ||
| 50 | #define __pte_free_tlb(tlb,pte) \ | 50 | #define __pte_free_tlb(tlb,pte,address) \ |
| 51 | do { \ | 51 | do { \ |
| 52 | pgtable_page_dtor(pte); \ | 52 | pgtable_page_dtor(pte); \ |
| 53 | tlb_remove_page((tlb), pte); \ | 53 | tlb_remove_page((tlb), pte); \ |
diff --git a/arch/frv/include/asm/pgalloc.h b/arch/frv/include/asm/pgalloc.h index 971e6addb009..416d19a632f2 100644 --- a/arch/frv/include/asm/pgalloc.h +++ b/arch/frv/include/asm/pgalloc.h | |||
| @@ -49,7 +49,7 @@ static inline void pte_free(struct mm_struct *mm, pgtable_t pte) | |||
| 49 | __free_page(pte); | 49 | __free_page(pte); |
| 50 | } | 50 | } |
| 51 | 51 | ||
| 52 | #define __pte_free_tlb(tlb,pte) \ | 52 | #define __pte_free_tlb(tlb,pte,address) \ |
| 53 | do { \ | 53 | do { \ |
| 54 | pgtable_page_dtor(pte); \ | 54 | pgtable_page_dtor(pte); \ |
| 55 | tlb_remove_page((tlb),(pte)); \ | 55 | tlb_remove_page((tlb),(pte)); \ |
| @@ -62,7 +62,7 @@ do { \ | |||
| 62 | */ | 62 | */ |
| 63 | #define pmd_alloc_one(mm, addr) ({ BUG(); ((pmd_t *) 2); }) | 63 | #define pmd_alloc_one(mm, addr) ({ BUG(); ((pmd_t *) 2); }) |
| 64 | #define pmd_free(mm, x) do { } while (0) | 64 | #define pmd_free(mm, x) do { } while (0) |
| 65 | #define __pmd_free_tlb(tlb,x) do { } while (0) | 65 | #define __pmd_free_tlb(tlb,x,a) do { } while (0) |
| 66 | 66 | ||
| 67 | #endif /* CONFIG_MMU */ | 67 | #endif /* CONFIG_MMU */ |
| 68 | 68 | ||
diff --git a/arch/frv/include/asm/pgtable.h b/arch/frv/include/asm/pgtable.h index 33233011b1c1..22c60692b551 100644 --- a/arch/frv/include/asm/pgtable.h +++ b/arch/frv/include/asm/pgtable.h | |||
| @@ -225,7 +225,7 @@ static inline pud_t *pud_offset(pgd_t *pgd, unsigned long address) | |||
| 225 | */ | 225 | */ |
| 226 | #define pud_alloc_one(mm, address) NULL | 226 | #define pud_alloc_one(mm, address) NULL |
| 227 | #define pud_free(mm, x) do { } while (0) | 227 | #define pud_free(mm, x) do { } while (0) |
| 228 | #define __pud_free_tlb(tlb, x) do { } while (0) | 228 | #define __pud_free_tlb(tlb, x, address) do { } while (0) |
| 229 | 229 | ||
| 230 | /* | 230 | /* |
| 231 | * The "pud_xxx()" functions here are trivial for a folded two-level | 231 | * The "pud_xxx()" functions here are trivial for a folded two-level |
diff --git a/arch/ia64/include/asm/pgalloc.h b/arch/ia64/include/asm/pgalloc.h index b9ac1a6fc216..96a8d927db28 100644 --- a/arch/ia64/include/asm/pgalloc.h +++ b/arch/ia64/include/asm/pgalloc.h | |||
| @@ -48,7 +48,7 @@ static inline void pud_free(struct mm_struct *mm, pud_t *pud) | |||
| 48 | { | 48 | { |
| 49 | quicklist_free(0, NULL, pud); | 49 | quicklist_free(0, NULL, pud); |
| 50 | } | 50 | } |
| 51 | #define __pud_free_tlb(tlb, pud) pud_free((tlb)->mm, pud) | 51 | #define __pud_free_tlb(tlb, pud, address) pud_free((tlb)->mm, pud) |
| 52 | #endif /* CONFIG_PGTABLE_4 */ | 52 | #endif /* CONFIG_PGTABLE_4 */ |
| 53 | 53 | ||
| 54 | static inline void | 54 | static inline void |
| @@ -67,7 +67,7 @@ static inline void pmd_free(struct mm_struct *mm, pmd_t *pmd) | |||
| 67 | quicklist_free(0, NULL, pmd); | 67 | quicklist_free(0, NULL, pmd); |
| 68 | } | 68 | } |
| 69 | 69 | ||
| 70 | #define __pmd_free_tlb(tlb, pmd) pmd_free((tlb)->mm, pmd) | 70 | #define __pmd_free_tlb(tlb, pmd, address) pmd_free((tlb)->mm, pmd) |
| 71 | 71 | ||
| 72 | static inline void | 72 | static inline void |
| 73 | pmd_populate(struct mm_struct *mm, pmd_t * pmd_entry, pgtable_t pte) | 73 | pmd_populate(struct mm_struct *mm, pmd_t * pmd_entry, pgtable_t pte) |
| @@ -117,6 +117,6 @@ static inline void check_pgt_cache(void) | |||
| 117 | quicklist_trim(0, NULL, 25, 16); | 117 | quicklist_trim(0, NULL, 25, 16); |
| 118 | } | 118 | } |
| 119 | 119 | ||
| 120 | #define __pte_free_tlb(tlb, pte) pte_free((tlb)->mm, pte) | 120 | #define __pte_free_tlb(tlb, pte, address) pte_free((tlb)->mm, pte) |
| 121 | 121 | ||
| 122 | #endif /* _ASM_IA64_PGALLOC_H */ | 122 | #endif /* _ASM_IA64_PGALLOC_H */ |
diff --git a/arch/ia64/include/asm/tlb.h b/arch/ia64/include/asm/tlb.h index 20d8a39680c2..85d965cb19a0 100644 --- a/arch/ia64/include/asm/tlb.h +++ b/arch/ia64/include/asm/tlb.h | |||
| @@ -236,22 +236,22 @@ do { \ | |||
| 236 | __tlb_remove_tlb_entry(tlb, ptep, addr); \ | 236 | __tlb_remove_tlb_entry(tlb, ptep, addr); \ |
| 237 | } while (0) | 237 | } while (0) |
| 238 | 238 | ||
| 239 | #define pte_free_tlb(tlb, ptep) \ | 239 | #define pte_free_tlb(tlb, ptep, address) \ |
| 240 | do { \ | 240 | do { \ |
| 241 | tlb->need_flush = 1; \ | 241 | tlb->need_flush = 1; \ |
| 242 | __pte_free_tlb(tlb, ptep); \ | 242 | __pte_free_tlb(tlb, ptep, address); \ |
| 243 | } while (0) | 243 | } while (0) |
| 244 | 244 | ||
| 245 | #define pmd_free_tlb(tlb, ptep) \ | 245 | #define pmd_free_tlb(tlb, ptep, address) \ |
| 246 | do { \ | 246 | do { \ |
| 247 | tlb->need_flush = 1; \ | 247 | tlb->need_flush = 1; \ |
| 248 | __pmd_free_tlb(tlb, ptep); \ | 248 | __pmd_free_tlb(tlb, ptep, address); \ |
| 249 | } while (0) | 249 | } while (0) |
| 250 | 250 | ||
| 251 | #define pud_free_tlb(tlb, pudp) \ | 251 | #define pud_free_tlb(tlb, pudp, address) \ |
| 252 | do { \ | 252 | do { \ |
| 253 | tlb->need_flush = 1; \ | 253 | tlb->need_flush = 1; \ |
| 254 | __pud_free_tlb(tlb, pudp); \ | 254 | __pud_free_tlb(tlb, pudp, address); \ |
| 255 | } while (0) | 255 | } while (0) |
| 256 | 256 | ||
| 257 | #endif /* _ASM_IA64_TLB_H */ | 257 | #endif /* _ASM_IA64_TLB_H */ |
diff --git a/arch/m32r/include/asm/pgalloc.h b/arch/m32r/include/asm/pgalloc.h index f11a2b909cdb..0fc736198979 100644 --- a/arch/m32r/include/asm/pgalloc.h +++ b/arch/m32r/include/asm/pgalloc.h | |||
| @@ -58,7 +58,7 @@ static inline void pte_free(struct mm_struct *mm, pgtable_t pte) | |||
| 58 | __free_page(pte); | 58 | __free_page(pte); |
| 59 | } | 59 | } |
| 60 | 60 | ||
| 61 | #define __pte_free_tlb(tlb, pte) pte_free((tlb)->mm, (pte)) | 61 | #define __pte_free_tlb(tlb, pte, addr) pte_free((tlb)->mm, (pte)) |
| 62 | 62 | ||
| 63 | /* | 63 | /* |
| 64 | * allocating and freeing a pmd is trivial: the 1-entry pmd is | 64 | * allocating and freeing a pmd is trivial: the 1-entry pmd is |
| @@ -68,7 +68,7 @@ static inline void pte_free(struct mm_struct *mm, pgtable_t pte) | |||
| 68 | 68 | ||
| 69 | #define pmd_alloc_one(mm, addr) ({ BUG(); ((pmd_t *)2); }) | 69 | #define pmd_alloc_one(mm, addr) ({ BUG(); ((pmd_t *)2); }) |
| 70 | #define pmd_free(mm, x) do { } while (0) | 70 | #define pmd_free(mm, x) do { } while (0) |
| 71 | #define __pmd_free_tlb(tlb, x) do { } while (0) | 71 | #define __pmd_free_tlb(tlb, x, addr) do { } while (0) |
| 72 | #define pgd_populate(mm, pmd, pte) BUG() | 72 | #define pgd_populate(mm, pmd, pte) BUG() |
| 73 | 73 | ||
| 74 | #define check_pgt_cache() do { } while (0) | 74 | #define check_pgt_cache() do { } while (0) |
diff --git a/arch/m68k/include/asm/motorola_pgalloc.h b/arch/m68k/include/asm/motorola_pgalloc.h index d08bf6261df8..15ee4c74a9f0 100644 --- a/arch/m68k/include/asm/motorola_pgalloc.h +++ b/arch/m68k/include/asm/motorola_pgalloc.h | |||
| @@ -54,7 +54,8 @@ static inline void pte_free(struct mm_struct *mm, pgtable_t page) | |||
| 54 | __free_page(page); | 54 | __free_page(page); |
| 55 | } | 55 | } |
| 56 | 56 | ||
| 57 | static inline void __pte_free_tlb(struct mmu_gather *tlb, pgtable_t page) | 57 | static inline void __pte_free_tlb(struct mmu_gather *tlb, pgtable_t page, |
| 58 | unsigned long address) | ||
| 58 | { | 59 | { |
| 59 | pgtable_page_dtor(page); | 60 | pgtable_page_dtor(page); |
| 60 | cache_page(kmap(page)); | 61 | cache_page(kmap(page)); |
| @@ -73,7 +74,8 @@ static inline int pmd_free(struct mm_struct *mm, pmd_t *pmd) | |||
| 73 | return free_pointer_table(pmd); | 74 | return free_pointer_table(pmd); |
| 74 | } | 75 | } |
| 75 | 76 | ||
| 76 | static inline int __pmd_free_tlb(struct mmu_gather *tlb, pmd_t *pmd) | 77 | static inline int __pmd_free_tlb(struct mmu_gather *tlb, pmd_t *pmd, |
| 78 | unsigned long address) | ||
| 77 | { | 79 | { |
| 78 | return free_pointer_table(pmd); | 80 | return free_pointer_table(pmd); |
| 79 | } | 81 | } |
diff --git a/arch/m68k/include/asm/sun3_pgalloc.h b/arch/m68k/include/asm/sun3_pgalloc.h index d4c83f143816..48d80d5a666f 100644 --- a/arch/m68k/include/asm/sun3_pgalloc.h +++ b/arch/m68k/include/asm/sun3_pgalloc.h | |||
| @@ -32,7 +32,7 @@ static inline void pte_free(struct mm_struct *mm, pgtable_t page) | |||
| 32 | __free_page(page); | 32 | __free_page(page); |
| 33 | } | 33 | } |
| 34 | 34 | ||
| 35 | #define __pte_free_tlb(tlb,pte) \ | 35 | #define __pte_free_tlb(tlb,pte,addr) \ |
| 36 | do { \ | 36 | do { \ |
| 37 | pgtable_page_dtor(pte); \ | 37 | pgtable_page_dtor(pte); \ |
| 38 | tlb_remove_page((tlb), pte); \ | 38 | tlb_remove_page((tlb), pte); \ |
| @@ -80,7 +80,7 @@ static inline void pmd_populate(struct mm_struct *mm, pmd_t *pmd, pgtable_t page | |||
| 80 | * inside the pgd, so has no extra memory associated with it. | 80 | * inside the pgd, so has no extra memory associated with it. |
| 81 | */ | 81 | */ |
| 82 | #define pmd_free(mm, x) do { } while (0) | 82 | #define pmd_free(mm, x) do { } while (0) |
| 83 | #define __pmd_free_tlb(tlb, x) do { } while (0) | 83 | #define __pmd_free_tlb(tlb, x, addr) do { } while (0) |
| 84 | 84 | ||
| 85 | static inline void pgd_free(struct mm_struct *mm, pgd_t *pgd) | 85 | static inline void pgd_free(struct mm_struct *mm, pgd_t *pgd) |
| 86 | { | 86 | { |
diff --git a/arch/microblaze/include/asm/pgalloc.h b/arch/microblaze/include/asm/pgalloc.h index 59a757e46ba5..b0131da1387b 100644 --- a/arch/microblaze/include/asm/pgalloc.h +++ b/arch/microblaze/include/asm/pgalloc.h | |||
| @@ -180,7 +180,7 @@ extern inline void pte_free(struct mm_struct *mm, struct page *ptepage) | |||
| 180 | __free_page(ptepage); | 180 | __free_page(ptepage); |
| 181 | } | 181 | } |
| 182 | 182 | ||
| 183 | #define __pte_free_tlb(tlb, pte) pte_free((tlb)->mm, (pte)) | 183 | #define __pte_free_tlb(tlb, pte, addr) pte_free((tlb)->mm, (pte)) |
| 184 | 184 | ||
| 185 | #define pmd_populate(mm, pmd, pte) (pmd_val(*(pmd)) = page_address(pte)) | 185 | #define pmd_populate(mm, pmd, pte) (pmd_val(*(pmd)) = page_address(pte)) |
| 186 | 186 | ||
| @@ -193,7 +193,7 @@ extern inline void pte_free(struct mm_struct *mm, struct page *ptepage) | |||
| 193 | */ | 193 | */ |
| 194 | #define pmd_alloc_one(mm, address) ({ BUG(); ((pmd_t *)2); }) | 194 | #define pmd_alloc_one(mm, address) ({ BUG(); ((pmd_t *)2); }) |
| 195 | /*#define pmd_free(mm, x) do { } while (0)*/ | 195 | /*#define pmd_free(mm, x) do { } while (0)*/ |
| 196 | #define __pmd_free_tlb(tlb, x) do { } while (0) | 196 | #define __pmd_free_tlb(tlb, x, addr) do { } while (0) |
| 197 | #define pgd_populate(mm, pmd, pte) BUG() | 197 | #define pgd_populate(mm, pmd, pte) BUG() |
| 198 | 198 | ||
| 199 | extern int do_check_pgt_cache(int, int); | 199 | extern int do_check_pgt_cache(int, int); |
diff --git a/arch/mips/include/asm/pgalloc.h b/arch/mips/include/asm/pgalloc.h index 1275831dda29..f705735feefc 100644 --- a/arch/mips/include/asm/pgalloc.h +++ b/arch/mips/include/asm/pgalloc.h | |||
| @@ -98,7 +98,7 @@ static inline void pte_free(struct mm_struct *mm, pgtable_t pte) | |||
| 98 | __free_pages(pte, PTE_ORDER); | 98 | __free_pages(pte, PTE_ORDER); |
| 99 | } | 99 | } |
| 100 | 100 | ||
| 101 | #define __pte_free_tlb(tlb,pte) \ | 101 | #define __pte_free_tlb(tlb,pte,address) \ |
| 102 | do { \ | 102 | do { \ |
| 103 | pgtable_page_dtor(pte); \ | 103 | pgtable_page_dtor(pte); \ |
| 104 | tlb_remove_page((tlb), pte); \ | 104 | tlb_remove_page((tlb), pte); \ |
| @@ -111,7 +111,7 @@ do { \ | |||
| 111 | * inside the pgd, so has no extra memory associated with it. | 111 | * inside the pgd, so has no extra memory associated with it. |
| 112 | */ | 112 | */ |
| 113 | #define pmd_free(mm, x) do { } while (0) | 113 | #define pmd_free(mm, x) do { } while (0) |
| 114 | #define __pmd_free_tlb(tlb, x) do { } while (0) | 114 | #define __pmd_free_tlb(tlb, x, addr) do { } while (0) |
| 115 | 115 | ||
| 116 | #endif | 116 | #endif |
| 117 | 117 | ||
| @@ -132,7 +132,7 @@ static inline void pmd_free(struct mm_struct *mm, pmd_t *pmd) | |||
| 132 | free_pages((unsigned long)pmd, PMD_ORDER); | 132 | free_pages((unsigned long)pmd, PMD_ORDER); |
| 133 | } | 133 | } |
| 134 | 134 | ||
| 135 | #define __pmd_free_tlb(tlb, x) pmd_free((tlb)->mm, x) | 135 | #define __pmd_free_tlb(tlb, x, addr) pmd_free((tlb)->mm, x) |
| 136 | 136 | ||
| 137 | #endif | 137 | #endif |
| 138 | 138 | ||
diff --git a/arch/mn10300/include/asm/pgalloc.h b/arch/mn10300/include/asm/pgalloc.h index ec057e1bd4cf..a19f11327cd8 100644 --- a/arch/mn10300/include/asm/pgalloc.h +++ b/arch/mn10300/include/asm/pgalloc.h | |||
| @@ -51,6 +51,6 @@ static inline void pte_free(struct mm_struct *mm, struct page *pte) | |||
| 51 | } | 51 | } |
| 52 | 52 | ||
| 53 | 53 | ||
| 54 | #define __pte_free_tlb(tlb, pte) tlb_remove_page((tlb), (pte)) | 54 | #define __pte_free_tlb(tlb, pte, addr) tlb_remove_page((tlb), (pte)) |
| 55 | 55 | ||
| 56 | #endif /* _ASM_PGALLOC_H */ | 56 | #endif /* _ASM_PGALLOC_H */ |
diff --git a/arch/parisc/include/asm/tlb.h b/arch/parisc/include/asm/tlb.h index 383b1db310ee..07924903989e 100644 --- a/arch/parisc/include/asm/tlb.h +++ b/arch/parisc/include/asm/tlb.h | |||
| @@ -21,7 +21,7 @@ do { if (!(tlb)->fullmm) \ | |||
| 21 | 21 | ||
| 22 | #include <asm-generic/tlb.h> | 22 | #include <asm-generic/tlb.h> |
| 23 | 23 | ||
| 24 | #define __pmd_free_tlb(tlb, pmd) pmd_free((tlb)->mm, pmd) | 24 | #define __pmd_free_tlb(tlb, pmd, addr) pmd_free((tlb)->mm, pmd) |
| 25 | #define __pte_free_tlb(tlb, pte) pte_free((tlb)->mm, pte) | 25 | #define __pte_free_tlb(tlb, pte, addr) pte_free((tlb)->mm, pte) |
| 26 | 26 | ||
| 27 | #endif | 27 | #endif |
diff --git a/arch/powerpc/include/asm/pgalloc-32.h b/arch/powerpc/include/asm/pgalloc-32.h index 0815eb40acae..c9500d666a1d 100644 --- a/arch/powerpc/include/asm/pgalloc-32.h +++ b/arch/powerpc/include/asm/pgalloc-32.h | |||
| @@ -16,7 +16,7 @@ extern void pgd_free(struct mm_struct *mm, pgd_t *pgd); | |||
| 16 | */ | 16 | */ |
| 17 | /* #define pmd_alloc_one(mm,address) ({ BUG(); ((pmd_t *)2); }) */ | 17 | /* #define pmd_alloc_one(mm,address) ({ BUG(); ((pmd_t *)2); }) */ |
| 18 | #define pmd_free(mm, x) do { } while (0) | 18 | #define pmd_free(mm, x) do { } while (0) |
| 19 | #define __pmd_free_tlb(tlb,x) do { } while (0) | 19 | #define __pmd_free_tlb(tlb,x,a) do { } while (0) |
| 20 | /* #define pgd_populate(mm, pmd, pte) BUG() */ | 20 | /* #define pgd_populate(mm, pmd, pte) BUG() */ |
| 21 | 21 | ||
| 22 | #ifndef CONFIG_BOOKE | 22 | #ifndef CONFIG_BOOKE |
diff --git a/arch/powerpc/include/asm/pgalloc-64.h b/arch/powerpc/include/asm/pgalloc-64.h index afda2bdd860f..e6f069c4f713 100644 --- a/arch/powerpc/include/asm/pgalloc-64.h +++ b/arch/powerpc/include/asm/pgalloc-64.h | |||
| @@ -118,11 +118,11 @@ static inline void pgtable_free(pgtable_free_t pgf) | |||
| 118 | kmem_cache_free(pgtable_cache[cachenum], p); | 118 | kmem_cache_free(pgtable_cache[cachenum], p); |
| 119 | } | 119 | } |
| 120 | 120 | ||
| 121 | #define __pmd_free_tlb(tlb, pmd) \ | 121 | #define __pmd_free_tlb(tlb, pmd,addr) \ |
| 122 | pgtable_free_tlb(tlb, pgtable_free_cache(pmd, \ | 122 | pgtable_free_tlb(tlb, pgtable_free_cache(pmd, \ |
| 123 | PMD_CACHE_NUM, PMD_TABLE_SIZE-1)) | 123 | PMD_CACHE_NUM, PMD_TABLE_SIZE-1)) |
| 124 | #ifndef CONFIG_PPC_64K_PAGES | 124 | #ifndef CONFIG_PPC_64K_PAGES |
| 125 | #define __pud_free_tlb(tlb, pud) \ | 125 | #define __pud_free_tlb(tlb, pud, addr) \ |
| 126 | pgtable_free_tlb(tlb, pgtable_free_cache(pud, \ | 126 | pgtable_free_tlb(tlb, pgtable_free_cache(pud, \ |
| 127 | PUD_CACHE_NUM, PUD_TABLE_SIZE-1)) | 127 | PUD_CACHE_NUM, PUD_TABLE_SIZE-1)) |
| 128 | #endif /* CONFIG_PPC_64K_PAGES */ | 128 | #endif /* CONFIG_PPC_64K_PAGES */ |
diff --git a/arch/powerpc/include/asm/pgalloc.h b/arch/powerpc/include/asm/pgalloc.h index 5d8480265a77..1730e5e298d6 100644 --- a/arch/powerpc/include/asm/pgalloc.h +++ b/arch/powerpc/include/asm/pgalloc.h | |||
| @@ -38,14 +38,14 @@ static inline pgtable_free_t pgtable_free_cache(void *p, int cachenum, | |||
| 38 | extern void pgtable_free_tlb(struct mmu_gather *tlb, pgtable_free_t pgf); | 38 | extern void pgtable_free_tlb(struct mmu_gather *tlb, pgtable_free_t pgf); |
| 39 | 39 | ||
| 40 | #ifdef CONFIG_SMP | 40 | #ifdef CONFIG_SMP |
| 41 | #define __pte_free_tlb(tlb,ptepage) \ | 41 | #define __pte_free_tlb(tlb,ptepage,address) \ |
| 42 | do { \ | 42 | do { \ |
| 43 | pgtable_page_dtor(ptepage); \ | 43 | pgtable_page_dtor(ptepage); \ |
| 44 | pgtable_free_tlb(tlb, pgtable_free_cache(page_address(ptepage), \ | 44 | pgtable_free_tlb(tlb, pgtable_free_cache(page_address(ptepage), \ |
| 45 | PTE_NONCACHE_NUM, PTE_TABLE_SIZE-1)); \ | 45 | PTE_NONCACHE_NUM, PTE_TABLE_SIZE-1)); \ |
| 46 | } while (0) | 46 | } while (0) |
| 47 | #else | 47 | #else |
| 48 | #define __pte_free_tlb(tlb, pte) pte_free((tlb)->mm, (pte)) | 48 | #define __pte_free_tlb(tlb, pte, address) pte_free((tlb)->mm, (pte)) |
| 49 | #endif | 49 | #endif |
| 50 | 50 | ||
| 51 | 51 | ||
diff --git a/arch/powerpc/mm/hugetlbpage.c b/arch/powerpc/mm/hugetlbpage.c index 9920d6a7cf29..c46ef2ffa3d9 100644 --- a/arch/powerpc/mm/hugetlbpage.c +++ b/arch/powerpc/mm/hugetlbpage.c | |||
| @@ -305,7 +305,7 @@ static void hugetlb_free_pmd_range(struct mmu_gather *tlb, pud_t *pud, | |||
| 305 | 305 | ||
| 306 | pmd = pmd_offset(pud, start); | 306 | pmd = pmd_offset(pud, start); |
| 307 | pud_clear(pud); | 307 | pud_clear(pud); |
| 308 | pmd_free_tlb(tlb, pmd); | 308 | pmd_free_tlb(tlb, pmd, start); |
| 309 | } | 309 | } |
| 310 | 310 | ||
| 311 | static void hugetlb_free_pud_range(struct mmu_gather *tlb, pgd_t *pgd, | 311 | static void hugetlb_free_pud_range(struct mmu_gather *tlb, pgd_t *pgd, |
| @@ -348,7 +348,7 @@ static void hugetlb_free_pud_range(struct mmu_gather *tlb, pgd_t *pgd, | |||
| 348 | 348 | ||
| 349 | pud = pud_offset(pgd, start); | 349 | pud = pud_offset(pgd, start); |
| 350 | pgd_clear(pgd); | 350 | pgd_clear(pgd); |
| 351 | pud_free_tlb(tlb, pud); | 351 | pud_free_tlb(tlb, pud, start); |
| 352 | } | 352 | } |
| 353 | 353 | ||
| 354 | /* | 354 | /* |
diff --git a/arch/s390/include/asm/tlb.h b/arch/s390/include/asm/tlb.h index 3d8a96d39d9d..81150b053689 100644 --- a/arch/s390/include/asm/tlb.h +++ b/arch/s390/include/asm/tlb.h | |||
| @@ -96,7 +96,8 @@ static inline void tlb_remove_page(struct mmu_gather *tlb, struct page *page) | |||
| 96 | * pte_free_tlb frees a pte table and clears the CRSTE for the | 96 | * pte_free_tlb frees a pte table and clears the CRSTE for the |
| 97 | * page table from the tlb. | 97 | * page table from the tlb. |
| 98 | */ | 98 | */ |
| 99 | static inline void pte_free_tlb(struct mmu_gather *tlb, pgtable_t pte) | 99 | static inline void pte_free_tlb(struct mmu_gather *tlb, pgtable_t pte, |
| 100 | unsigned long address) | ||
| 100 | { | 101 | { |
| 101 | if (!tlb->fullmm) { | 102 | if (!tlb->fullmm) { |
| 102 | tlb->array[tlb->nr_ptes++] = pte; | 103 | tlb->array[tlb->nr_ptes++] = pte; |
| @@ -113,7 +114,8 @@ static inline void pte_free_tlb(struct mmu_gather *tlb, pgtable_t pte) | |||
| 113 | * as the pgd. pmd_free_tlb checks the asce_limit against 2GB | 114 | * as the pgd. pmd_free_tlb checks the asce_limit against 2GB |
| 114 | * to avoid the double free of the pmd in this case. | 115 | * to avoid the double free of the pmd in this case. |
| 115 | */ | 116 | */ |
| 116 | static inline void pmd_free_tlb(struct mmu_gather *tlb, pmd_t *pmd) | 117 | static inline void pmd_free_tlb(struct mmu_gather *tlb, pmd_t *pmd, |
| 118 | unsigned long address) | ||
| 117 | { | 119 | { |
| 118 | #ifdef __s390x__ | 120 | #ifdef __s390x__ |
| 119 | if (tlb->mm->context.asce_limit <= (1UL << 31)) | 121 | if (tlb->mm->context.asce_limit <= (1UL << 31)) |
| @@ -134,7 +136,8 @@ static inline void pmd_free_tlb(struct mmu_gather *tlb, pmd_t *pmd) | |||
| 134 | * as the pgd. pud_free_tlb checks the asce_limit against 4TB | 136 | * as the pgd. pud_free_tlb checks the asce_limit against 4TB |
| 135 | * to avoid the double free of the pud in this case. | 137 | * to avoid the double free of the pud in this case. |
| 136 | */ | 138 | */ |
| 137 | static inline void pud_free_tlb(struct mmu_gather *tlb, pud_t *pud) | 139 | static inline void pud_free_tlb(struct mmu_gather *tlb, pud_t *pud, |
| 140 | unsigned long address) | ||
| 138 | { | 141 | { |
| 139 | #ifdef __s390x__ | 142 | #ifdef __s390x__ |
| 140 | if (tlb->mm->context.asce_limit <= (1UL << 42)) | 143 | if (tlb->mm->context.asce_limit <= (1UL << 42)) |
diff --git a/arch/sh/include/asm/pgalloc.h b/arch/sh/include/asm/pgalloc.h index 84dd2db7104c..89a482750a5b 100644 --- a/arch/sh/include/asm/pgalloc.h +++ b/arch/sh/include/asm/pgalloc.h | |||
| @@ -73,7 +73,7 @@ static inline void pte_free(struct mm_struct *mm, pgtable_t pte) | |||
| 73 | quicklist_free_page(QUICK_PT, NULL, pte); | 73 | quicklist_free_page(QUICK_PT, NULL, pte); |
| 74 | } | 74 | } |
| 75 | 75 | ||
| 76 | #define __pte_free_tlb(tlb,pte) \ | 76 | #define __pte_free_tlb(tlb,pte,addr) \ |
| 77 | do { \ | 77 | do { \ |
| 78 | pgtable_page_dtor(pte); \ | 78 | pgtable_page_dtor(pte); \ |
| 79 | tlb_remove_page((tlb), (pte)); \ | 79 | tlb_remove_page((tlb), (pte)); \ |
| @@ -85,7 +85,7 @@ do { \ | |||
| 85 | */ | 85 | */ |
| 86 | 86 | ||
| 87 | #define pmd_free(mm, x) do { } while (0) | 87 | #define pmd_free(mm, x) do { } while (0) |
| 88 | #define __pmd_free_tlb(tlb,x) do { } while (0) | 88 | #define __pmd_free_tlb(tlb,x,addr) do { } while (0) |
| 89 | 89 | ||
| 90 | static inline void check_pgt_cache(void) | 90 | static inline void check_pgt_cache(void) |
| 91 | { | 91 | { |
diff --git a/arch/sh/include/asm/tlb.h b/arch/sh/include/asm/tlb.h index 9c16f737074a..da8fe7ab8728 100644 --- a/arch/sh/include/asm/tlb.h +++ b/arch/sh/include/asm/tlb.h | |||
| @@ -91,9 +91,9 @@ tlb_end_vma(struct mmu_gather *tlb, struct vm_area_struct *vma) | |||
| 91 | } | 91 | } |
| 92 | 92 | ||
| 93 | #define tlb_remove_page(tlb,page) free_page_and_swap_cache(page) | 93 | #define tlb_remove_page(tlb,page) free_page_and_swap_cache(page) |
| 94 | #define pte_free_tlb(tlb, ptep) pte_free((tlb)->mm, ptep) | 94 | #define pte_free_tlb(tlb, ptep, addr) pte_free((tlb)->mm, ptep) |
| 95 | #define pmd_free_tlb(tlb, pmdp) pmd_free((tlb)->mm, pmdp) | 95 | #define pmd_free_tlb(tlb, pmdp, addr) pmd_free((tlb)->mm, pmdp) |
| 96 | #define pud_free_tlb(tlb, pudp) pud_free((tlb)->mm, pudp) | 96 | #define pud_free_tlb(tlb, pudp, addr) pud_free((tlb)->mm, pudp) |
| 97 | 97 | ||
| 98 | #define tlb_migrate_finish(mm) do { } while (0) | 98 | #define tlb_migrate_finish(mm) do { } while (0) |
| 99 | 99 | ||
diff --git a/arch/sparc/include/asm/pgalloc_32.h b/arch/sparc/include/asm/pgalloc_32.h index 681582d26969..ca2b34456c4b 100644 --- a/arch/sparc/include/asm/pgalloc_32.h +++ b/arch/sparc/include/asm/pgalloc_32.h | |||
| @@ -44,8 +44,8 @@ BTFIXUPDEF_CALL(pmd_t *, pmd_alloc_one, struct mm_struct *, unsigned long) | |||
| 44 | BTFIXUPDEF_CALL(void, free_pmd_fast, pmd_t *) | 44 | BTFIXUPDEF_CALL(void, free_pmd_fast, pmd_t *) |
| 45 | #define free_pmd_fast(pmd) BTFIXUP_CALL(free_pmd_fast)(pmd) | 45 | #define free_pmd_fast(pmd) BTFIXUP_CALL(free_pmd_fast)(pmd) |
| 46 | 46 | ||
| 47 | #define pmd_free(mm, pmd) free_pmd_fast(pmd) | 47 | #define pmd_free(mm, pmd) free_pmd_fast(pmd) |
| 48 | #define __pmd_free_tlb(tlb, pmd) pmd_free((tlb)->mm, pmd) | 48 | #define __pmd_free_tlb(tlb, pmd, addr) pmd_free((tlb)->mm, pmd) |
| 49 | 49 | ||
| 50 | BTFIXUPDEF_CALL(void, pmd_populate, pmd_t *, struct page *) | 50 | BTFIXUPDEF_CALL(void, pmd_populate, pmd_t *, struct page *) |
| 51 | #define pmd_populate(MM, PMD, PTE) BTFIXUP_CALL(pmd_populate)(PMD, PTE) | 51 | #define pmd_populate(MM, PMD, PTE) BTFIXUP_CALL(pmd_populate)(PMD, PTE) |
| @@ -62,7 +62,7 @@ BTFIXUPDEF_CALL(void, free_pte_fast, pte_t *) | |||
| 62 | #define pte_free_kernel(mm, pte) BTFIXUP_CALL(free_pte_fast)(pte) | 62 | #define pte_free_kernel(mm, pte) BTFIXUP_CALL(free_pte_fast)(pte) |
| 63 | 63 | ||
| 64 | BTFIXUPDEF_CALL(void, pte_free, pgtable_t ) | 64 | BTFIXUPDEF_CALL(void, pte_free, pgtable_t ) |
| 65 | #define pte_free(mm, pte) BTFIXUP_CALL(pte_free)(pte) | 65 | #define pte_free(mm, pte) BTFIXUP_CALL(pte_free)(pte) |
| 66 | #define __pte_free_tlb(tlb, pte) pte_free((tlb)->mm, pte) | 66 | #define __pte_free_tlb(tlb, pte, addr) pte_free((tlb)->mm, pte) |
| 67 | 67 | ||
| 68 | #endif /* _SPARC_PGALLOC_H */ | 68 | #endif /* _SPARC_PGALLOC_H */ |
diff --git a/arch/sparc/include/asm/tlb_64.h b/arch/sparc/include/asm/tlb_64.h index ee38e731bfa6..dca406b9b6fc 100644 --- a/arch/sparc/include/asm/tlb_64.h +++ b/arch/sparc/include/asm/tlb_64.h | |||
| @@ -100,9 +100,9 @@ static inline void tlb_remove_page(struct mmu_gather *mp, struct page *page) | |||
| 100 | } | 100 | } |
| 101 | 101 | ||
| 102 | #define tlb_remove_tlb_entry(mp,ptep,addr) do { } while (0) | 102 | #define tlb_remove_tlb_entry(mp,ptep,addr) do { } while (0) |
| 103 | #define pte_free_tlb(mp, ptepage) pte_free((mp)->mm, ptepage) | 103 | #define pte_free_tlb(mp, ptepage, addr) pte_free((mp)->mm, ptepage) |
| 104 | #define pmd_free_tlb(mp, pmdp) pmd_free((mp)->mm, pmdp) | 104 | #define pmd_free_tlb(mp, pmdp, addr) pmd_free((mp)->mm, pmdp) |
| 105 | #define pud_free_tlb(tlb,pudp) __pud_free_tlb(tlb,pudp) | 105 | #define pud_free_tlb(tlb,pudp, addr) __pud_free_tlb(tlb,pudp,addr) |
| 106 | 106 | ||
| 107 | #define tlb_migrate_finish(mm) do { } while (0) | 107 | #define tlb_migrate_finish(mm) do { } while (0) |
| 108 | #define tlb_start_vma(tlb, vma) do { } while (0) | 108 | #define tlb_start_vma(tlb, vma) do { } while (0) |
diff --git a/arch/um/include/asm/pgalloc.h b/arch/um/include/asm/pgalloc.h index 718984359f8c..32c8ce4e1515 100644 --- a/arch/um/include/asm/pgalloc.h +++ b/arch/um/include/asm/pgalloc.h | |||
| @@ -40,7 +40,7 @@ static inline void pte_free(struct mm_struct *mm, pgtable_t pte) | |||
| 40 | __free_page(pte); | 40 | __free_page(pte); |
| 41 | } | 41 | } |
| 42 | 42 | ||
| 43 | #define __pte_free_tlb(tlb,pte) \ | 43 | #define __pte_free_tlb(tlb,pte, address) \ |
| 44 | do { \ | 44 | do { \ |
| 45 | pgtable_page_dtor(pte); \ | 45 | pgtable_page_dtor(pte); \ |
| 46 | tlb_remove_page((tlb),(pte)); \ | 46 | tlb_remove_page((tlb),(pte)); \ |
| @@ -53,7 +53,7 @@ static inline void pmd_free(struct mm_struct *mm, pmd_t *pmd) | |||
| 53 | free_page((unsigned long)pmd); | 53 | free_page((unsigned long)pmd); |
| 54 | } | 54 | } |
| 55 | 55 | ||
| 56 | #define __pmd_free_tlb(tlb,x) tlb_remove_page((tlb),virt_to_page(x)) | 56 | #define __pmd_free_tlb(tlb,x, address) tlb_remove_page((tlb),virt_to_page(x)) |
| 57 | #endif | 57 | #endif |
| 58 | 58 | ||
| 59 | #define check_pgt_cache() do { } while (0) | 59 | #define check_pgt_cache() do { } while (0) |
diff --git a/arch/um/include/asm/tlb.h b/arch/um/include/asm/tlb.h index 5240fa1c5e08..660caedac9eb 100644 --- a/arch/um/include/asm/tlb.h +++ b/arch/um/include/asm/tlb.h | |||
| @@ -116,11 +116,11 @@ static inline void tlb_remove_page(struct mmu_gather *tlb, struct page *page) | |||
| 116 | __tlb_remove_tlb_entry(tlb, ptep, address); \ | 116 | __tlb_remove_tlb_entry(tlb, ptep, address); \ |
| 117 | } while (0) | 117 | } while (0) |
| 118 | 118 | ||
| 119 | #define pte_free_tlb(tlb, ptep) __pte_free_tlb(tlb, ptep) | 119 | #define pte_free_tlb(tlb, ptep, addr) __pte_free_tlb(tlb, ptep, addr) |
| 120 | 120 | ||
| 121 | #define pud_free_tlb(tlb, pudp) __pud_free_tlb(tlb, pudp) | 121 | #define pud_free_tlb(tlb, pudp, addr) __pud_free_tlb(tlb, pudp, addr) |
| 122 | 122 | ||
| 123 | #define pmd_free_tlb(tlb, pmdp) __pmd_free_tlb(tlb, pmdp) | 123 | #define pmd_free_tlb(tlb, pmdp, addr) __pmd_free_tlb(tlb, pmdp, addr) |
| 124 | 124 | ||
| 125 | #define tlb_migrate_finish(mm) do {} while (0) | 125 | #define tlb_migrate_finish(mm) do {} while (0) |
| 126 | 126 | ||
diff --git a/arch/x86/include/asm/pgalloc.h b/arch/x86/include/asm/pgalloc.h index dd14c54ac718..0e8c2a0fd922 100644 --- a/arch/x86/include/asm/pgalloc.h +++ b/arch/x86/include/asm/pgalloc.h | |||
| @@ -46,7 +46,13 @@ static inline void pte_free(struct mm_struct *mm, struct page *pte) | |||
| 46 | __free_page(pte); | 46 | __free_page(pte); |
| 47 | } | 47 | } |
| 48 | 48 | ||
| 49 | extern void __pte_free_tlb(struct mmu_gather *tlb, struct page *pte); | 49 | extern void ___pte_free_tlb(struct mmu_gather *tlb, struct page *pte); |
| 50 | |||
| 51 | static inline void __pte_free_tlb(struct mmu_gather *tlb, struct page *pte, | ||
| 52 | unsigned long address) | ||
| 53 | { | ||
| 54 | ___pte_free_tlb(tlb, pte); | ||
| 55 | } | ||
| 50 | 56 | ||
| 51 | static inline void pmd_populate_kernel(struct mm_struct *mm, | 57 | static inline void pmd_populate_kernel(struct mm_struct *mm, |
| 52 | pmd_t *pmd, pte_t *pte) | 58 | pmd_t *pmd, pte_t *pte) |
| @@ -78,7 +84,13 @@ static inline void pmd_free(struct mm_struct *mm, pmd_t *pmd) | |||
| 78 | free_page((unsigned long)pmd); | 84 | free_page((unsigned long)pmd); |
| 79 | } | 85 | } |
| 80 | 86 | ||
| 81 | extern void __pmd_free_tlb(struct mmu_gather *tlb, pmd_t *pmd); | 87 | extern void ___pmd_free_tlb(struct mmu_gather *tlb, pmd_t *pmd); |
| 88 | |||
| 89 | static inline void __pmd_free_tlb(struct mmu_gather *tlb, pmd_t *pmd, | ||
| 90 | unsigned long adddress) | ||
| 91 | { | ||
| 92 | ___pmd_free_tlb(tlb, pmd); | ||
| 93 | } | ||
| 82 | 94 | ||
| 83 | #ifdef CONFIG_X86_PAE | 95 | #ifdef CONFIG_X86_PAE |
| 84 | extern void pud_populate(struct mm_struct *mm, pud_t *pudp, pmd_t *pmd); | 96 | extern void pud_populate(struct mm_struct *mm, pud_t *pudp, pmd_t *pmd); |
| @@ -108,7 +120,14 @@ static inline void pud_free(struct mm_struct *mm, pud_t *pud) | |||
| 108 | free_page((unsigned long)pud); | 120 | free_page((unsigned long)pud); |
| 109 | } | 121 | } |
| 110 | 122 | ||
| 111 | extern void __pud_free_tlb(struct mmu_gather *tlb, pud_t *pud); | 123 | extern void ___pud_free_tlb(struct mmu_gather *tlb, pud_t *pud); |
| 124 | |||
| 125 | static inline void __pud_free_tlb(struct mmu_gather *tlb, pud_t *pud, | ||
| 126 | unsigned long address) | ||
| 127 | { | ||
| 128 | ___pud_free_tlb(tlb, pud); | ||
| 129 | } | ||
| 130 | |||
| 112 | #endif /* PAGETABLE_LEVELS > 3 */ | 131 | #endif /* PAGETABLE_LEVELS > 3 */ |
| 113 | #endif /* PAGETABLE_LEVELS > 2 */ | 132 | #endif /* PAGETABLE_LEVELS > 2 */ |
| 114 | 133 | ||
diff --git a/arch/x86/mm/pgtable.c b/arch/x86/mm/pgtable.c index 8e43bdd45456..af8f9650058c 100644 --- a/arch/x86/mm/pgtable.c +++ b/arch/x86/mm/pgtable.c | |||
| @@ -25,7 +25,7 @@ pgtable_t pte_alloc_one(struct mm_struct *mm, unsigned long address) | |||
| 25 | return pte; | 25 | return pte; |
| 26 | } | 26 | } |
| 27 | 27 | ||
| 28 | void __pte_free_tlb(struct mmu_gather *tlb, struct page *pte) | 28 | void ___pte_free_tlb(struct mmu_gather *tlb, struct page *pte) |
| 29 | { | 29 | { |
| 30 | pgtable_page_dtor(pte); | 30 | pgtable_page_dtor(pte); |
| 31 | paravirt_release_pte(page_to_pfn(pte)); | 31 | paravirt_release_pte(page_to_pfn(pte)); |
| @@ -33,14 +33,14 @@ void __pte_free_tlb(struct mmu_gather *tlb, struct page *pte) | |||
| 33 | } | 33 | } |
| 34 | 34 | ||
| 35 | #if PAGETABLE_LEVELS > 2 | 35 | #if PAGETABLE_LEVELS > 2 |
| 36 | void __pmd_free_tlb(struct mmu_gather *tlb, pmd_t *pmd) | 36 | void ___pmd_free_tlb(struct mmu_gather *tlb, pmd_t *pmd) |
| 37 | { | 37 | { |
| 38 | paravirt_release_pmd(__pa(pmd) >> PAGE_SHIFT); | 38 | paravirt_release_pmd(__pa(pmd) >> PAGE_SHIFT); |
| 39 | tlb_remove_page(tlb, virt_to_page(pmd)); | 39 | tlb_remove_page(tlb, virt_to_page(pmd)); |
| 40 | } | 40 | } |
| 41 | 41 | ||
| 42 | #if PAGETABLE_LEVELS > 3 | 42 | #if PAGETABLE_LEVELS > 3 |
| 43 | void __pud_free_tlb(struct mmu_gather *tlb, pud_t *pud) | 43 | void ___pud_free_tlb(struct mmu_gather *tlb, pud_t *pud) |
| 44 | { | 44 | { |
| 45 | paravirt_release_pud(__pa(pud) >> PAGE_SHIFT); | 45 | paravirt_release_pud(__pa(pud) >> PAGE_SHIFT); |
| 46 | tlb_remove_page(tlb, virt_to_page(pud)); | 46 | tlb_remove_page(tlb, virt_to_page(pud)); |
diff --git a/arch/xtensa/include/asm/tlb.h b/arch/xtensa/include/asm/tlb.h index 31c220faca02..0d766f9c1083 100644 --- a/arch/xtensa/include/asm/tlb.h +++ b/arch/xtensa/include/asm/tlb.h | |||
| @@ -42,6 +42,6 @@ | |||
| 42 | 42 | ||
| 43 | #include <asm-generic/tlb.h> | 43 | #include <asm-generic/tlb.h> |
| 44 | 44 | ||
| 45 | #define __pte_free_tlb(tlb, pte) pte_free((tlb)->mm, pte) | 45 | #define __pte_free_tlb(tlb, pte, address) pte_free((tlb)->mm, pte) |
| 46 | 46 | ||
| 47 | #endif /* _XTENSA_TLB_H */ | 47 | #endif /* _XTENSA_TLB_H */ |
diff --git a/fs/cifs/connect.c b/fs/cifs/connect.c index 9bb5c8750736..fc44d316d0bb 100644 --- a/fs/cifs/connect.c +++ b/fs/cifs/connect.c | |||
| @@ -2452,10 +2452,10 @@ try_mount_again: | |||
| 2452 | tcon->local_lease = volume_info->local_lease; | 2452 | tcon->local_lease = volume_info->local_lease; |
| 2453 | } | 2453 | } |
| 2454 | if (pSesInfo) { | 2454 | if (pSesInfo) { |
| 2455 | if (pSesInfo->capabilities & CAP_LARGE_FILES) { | 2455 | if (pSesInfo->capabilities & CAP_LARGE_FILES) |
| 2456 | sb->s_maxbytes = (u64) 1 << 63; | 2456 | sb->s_maxbytes = MAX_LFS_FILESIZE; |
| 2457 | } else | 2457 | else |
| 2458 | sb->s_maxbytes = (u64) 1 << 31; /* 2 GB */ | 2458 | sb->s_maxbytes = MAX_NON_LFS; |
| 2459 | } | 2459 | } |
| 2460 | 2460 | ||
| 2461 | /* BB FIXME fix time_gran to be larger for LANMAN sessions */ | 2461 | /* BB FIXME fix time_gran to be larger for LANMAN sessions */ |
diff --git a/fs/cifs/inode.c b/fs/cifs/inode.c index 18afe57b2461..82d83839655e 100644 --- a/fs/cifs/inode.c +++ b/fs/cifs/inode.c | |||
| @@ -212,7 +212,7 @@ cifs_unix_basic_to_fattr(struct cifs_fattr *fattr, FILE_UNIX_BASIC_INFO *info, | |||
| 212 | * junction to the new submount (ie to setup the fake directory | 212 | * junction to the new submount (ie to setup the fake directory |
| 213 | * which represents a DFS referral). | 213 | * which represents a DFS referral). |
| 214 | */ | 214 | */ |
| 215 | void | 215 | static void |
| 216 | cifs_create_dfs_fattr(struct cifs_fattr *fattr, struct super_block *sb) | 216 | cifs_create_dfs_fattr(struct cifs_fattr *fattr, struct super_block *sb) |
| 217 | { | 217 | { |
| 218 | struct cifs_sb_info *cifs_sb = CIFS_SB(sb); | 218 | struct cifs_sb_info *cifs_sb = CIFS_SB(sb); |
| @@ -388,7 +388,7 @@ static int cifs_sfu_mode(struct cifs_fattr *fattr, const unsigned char *path, | |||
| 388 | } | 388 | } |
| 389 | 389 | ||
| 390 | /* Fill a cifs_fattr struct with info from FILE_ALL_INFO */ | 390 | /* Fill a cifs_fattr struct with info from FILE_ALL_INFO */ |
| 391 | void | 391 | static void |
| 392 | cifs_all_info_to_fattr(struct cifs_fattr *fattr, FILE_ALL_INFO *info, | 392 | cifs_all_info_to_fattr(struct cifs_fattr *fattr, FILE_ALL_INFO *info, |
| 393 | struct cifs_sb_info *cifs_sb, bool adjust_tz) | 393 | struct cifs_sb_info *cifs_sb, bool adjust_tz) |
| 394 | { | 394 | { |
| @@ -513,9 +513,12 @@ int cifs_get_inode_info(struct inode **pinode, | |||
| 513 | cifs_sb->mnt_cifs_flags & | 513 | cifs_sb->mnt_cifs_flags & |
| 514 | CIFS_MOUNT_MAP_SPECIAL_CHR); | 514 | CIFS_MOUNT_MAP_SPECIAL_CHR); |
| 515 | if (rc1) { | 515 | if (rc1) { |
| 516 | /* BB EOPNOSUPP disable SERVER_INUM? */ | ||
| 517 | cFYI(1, ("GetSrvInodeNum rc %d", rc1)); | 516 | cFYI(1, ("GetSrvInodeNum rc %d", rc1)); |
| 518 | fattr.cf_uniqueid = iunique(sb, ROOT_I); | 517 | fattr.cf_uniqueid = iunique(sb, ROOT_I); |
| 518 | /* disable serverino if call not supported */ | ||
| 519 | if (rc1 == -EINVAL) | ||
| 520 | cifs_sb->mnt_cifs_flags &= | ||
| 521 | ~CIFS_MOUNT_SERVER_INUM; | ||
| 519 | } | 522 | } |
| 520 | } else { | 523 | } else { |
| 521 | fattr.cf_uniqueid = iunique(sb, ROOT_I); | 524 | fattr.cf_uniqueid = iunique(sb, ROOT_I); |
diff --git a/fs/ext3/dir.c b/fs/ext3/dir.c index 3d724a95882f..373fa90c796a 100644 --- a/fs/ext3/dir.c +++ b/fs/ext3/dir.c | |||
| @@ -130,8 +130,7 @@ static int ext3_readdir(struct file * filp, | |||
| 130 | struct buffer_head *bh = NULL; | 130 | struct buffer_head *bh = NULL; |
| 131 | 131 | ||
| 132 | map_bh.b_state = 0; | 132 | map_bh.b_state = 0; |
| 133 | err = ext3_get_blocks_handle(NULL, inode, blk, 1, | 133 | err = ext3_get_blocks_handle(NULL, inode, blk, 1, &map_bh, 0); |
| 134 | &map_bh, 0, 0); | ||
| 135 | if (err > 0) { | 134 | if (err > 0) { |
| 136 | pgoff_t index = map_bh.b_blocknr >> | 135 | pgoff_t index = map_bh.b_blocknr >> |
| 137 | (PAGE_CACHE_SHIFT - inode->i_blkbits); | 136 | (PAGE_CACHE_SHIFT - inode->i_blkbits); |
diff --git a/fs/ext3/inode.c b/fs/ext3/inode.c index 5f51fed5c750..b49908a167ae 100644 --- a/fs/ext3/inode.c +++ b/fs/ext3/inode.c | |||
| @@ -788,7 +788,7 @@ err_out: | |||
| 788 | int ext3_get_blocks_handle(handle_t *handle, struct inode *inode, | 788 | int ext3_get_blocks_handle(handle_t *handle, struct inode *inode, |
| 789 | sector_t iblock, unsigned long maxblocks, | 789 | sector_t iblock, unsigned long maxblocks, |
| 790 | struct buffer_head *bh_result, | 790 | struct buffer_head *bh_result, |
| 791 | int create, int extend_disksize) | 791 | int create) |
| 792 | { | 792 | { |
| 793 | int err = -EIO; | 793 | int err = -EIO; |
| 794 | int offsets[4]; | 794 | int offsets[4]; |
| @@ -911,13 +911,6 @@ int ext3_get_blocks_handle(handle_t *handle, struct inode *inode, | |||
| 911 | if (!err) | 911 | if (!err) |
| 912 | err = ext3_splice_branch(handle, inode, iblock, | 912 | err = ext3_splice_branch(handle, inode, iblock, |
| 913 | partial, indirect_blks, count); | 913 | partial, indirect_blks, count); |
| 914 | /* | ||
| 915 | * i_disksize growing is protected by truncate_mutex. Don't forget to | ||
| 916 | * protect it if you're about to implement concurrent | ||
| 917 | * ext3_get_block() -bzzz | ||
| 918 | */ | ||
| 919 | if (!err && extend_disksize && inode->i_size > ei->i_disksize) | ||
| 920 | ei->i_disksize = inode->i_size; | ||
| 921 | mutex_unlock(&ei->truncate_mutex); | 914 | mutex_unlock(&ei->truncate_mutex); |
| 922 | if (err) | 915 | if (err) |
| 923 | goto cleanup; | 916 | goto cleanup; |
| @@ -972,7 +965,7 @@ static int ext3_get_block(struct inode *inode, sector_t iblock, | |||
| 972 | } | 965 | } |
| 973 | 966 | ||
| 974 | ret = ext3_get_blocks_handle(handle, inode, iblock, | 967 | ret = ext3_get_blocks_handle(handle, inode, iblock, |
| 975 | max_blocks, bh_result, create, 0); | 968 | max_blocks, bh_result, create); |
| 976 | if (ret > 0) { | 969 | if (ret > 0) { |
| 977 | bh_result->b_size = (ret << inode->i_blkbits); | 970 | bh_result->b_size = (ret << inode->i_blkbits); |
| 978 | ret = 0; | 971 | ret = 0; |
| @@ -1005,7 +998,7 @@ struct buffer_head *ext3_getblk(handle_t *handle, struct inode *inode, | |||
| 1005 | dummy.b_blocknr = -1000; | 998 | dummy.b_blocknr = -1000; |
| 1006 | buffer_trace_init(&dummy.b_history); | 999 | buffer_trace_init(&dummy.b_history); |
| 1007 | err = ext3_get_blocks_handle(handle, inode, block, 1, | 1000 | err = ext3_get_blocks_handle(handle, inode, block, 1, |
| 1008 | &dummy, create, 1); | 1001 | &dummy, create); |
| 1009 | /* | 1002 | /* |
| 1010 | * ext3_get_blocks_handle() returns number of blocks | 1003 | * ext3_get_blocks_handle() returns number of blocks |
| 1011 | * mapped. 0 in case of a HOLE. | 1004 | * mapped. 0 in case of a HOLE. |
| @@ -1193,15 +1186,16 @@ write_begin_failed: | |||
| 1193 | * i_size_read because we hold i_mutex. | 1186 | * i_size_read because we hold i_mutex. |
| 1194 | * | 1187 | * |
| 1195 | * Add inode to orphan list in case we crash before truncate | 1188 | * Add inode to orphan list in case we crash before truncate |
| 1196 | * finishes. | 1189 | * finishes. Do this only if ext3_can_truncate() agrees so |
| 1190 | * that orphan processing code is happy. | ||
| 1197 | */ | 1191 | */ |
| 1198 | if (pos + len > inode->i_size) | 1192 | if (pos + len > inode->i_size && ext3_can_truncate(inode)) |
| 1199 | ext3_orphan_add(handle, inode); | 1193 | ext3_orphan_add(handle, inode); |
| 1200 | ext3_journal_stop(handle); | 1194 | ext3_journal_stop(handle); |
| 1201 | unlock_page(page); | 1195 | unlock_page(page); |
| 1202 | page_cache_release(page); | 1196 | page_cache_release(page); |
| 1203 | if (pos + len > inode->i_size) | 1197 | if (pos + len > inode->i_size) |
| 1204 | vmtruncate(inode, inode->i_size); | 1198 | ext3_truncate(inode); |
| 1205 | } | 1199 | } |
| 1206 | if (ret == -ENOSPC && ext3_should_retry_alloc(inode->i_sb, &retries)) | 1200 | if (ret == -ENOSPC && ext3_should_retry_alloc(inode->i_sb, &retries)) |
| 1207 | goto retry; | 1201 | goto retry; |
| @@ -1287,7 +1281,7 @@ static int ext3_ordered_write_end(struct file *file, | |||
| 1287 | * There may be allocated blocks outside of i_size because | 1281 | * There may be allocated blocks outside of i_size because |
| 1288 | * we failed to copy some data. Prepare for truncate. | 1282 | * we failed to copy some data. Prepare for truncate. |
| 1289 | */ | 1283 | */ |
| 1290 | if (pos + len > inode->i_size) | 1284 | if (pos + len > inode->i_size && ext3_can_truncate(inode)) |
| 1291 | ext3_orphan_add(handle, inode); | 1285 | ext3_orphan_add(handle, inode); |
| 1292 | ret2 = ext3_journal_stop(handle); | 1286 | ret2 = ext3_journal_stop(handle); |
| 1293 | if (!ret) | 1287 | if (!ret) |
| @@ -1296,7 +1290,7 @@ static int ext3_ordered_write_end(struct file *file, | |||
| 1296 | page_cache_release(page); | 1290 | page_cache_release(page); |
| 1297 | 1291 | ||
| 1298 | if (pos + len > inode->i_size) | 1292 | if (pos + len > inode->i_size) |
| 1299 | vmtruncate(inode, inode->i_size); | 1293 | ext3_truncate(inode); |
| 1300 | return ret ? ret : copied; | 1294 | return ret ? ret : copied; |
| 1301 | } | 1295 | } |
| 1302 | 1296 | ||
| @@ -1315,14 +1309,14 @@ static int ext3_writeback_write_end(struct file *file, | |||
| 1315 | * There may be allocated blocks outside of i_size because | 1309 | * There may be allocated blocks outside of i_size because |
| 1316 | * we failed to copy some data. Prepare for truncate. | 1310 | * we failed to copy some data. Prepare for truncate. |
| 1317 | */ | 1311 | */ |
| 1318 | if (pos + len > inode->i_size) | 1312 | if (pos + len > inode->i_size && ext3_can_truncate(inode)) |
| 1319 | ext3_orphan_add(handle, inode); | 1313 | ext3_orphan_add(handle, inode); |
| 1320 | ret = ext3_journal_stop(handle); | 1314 | ret = ext3_journal_stop(handle); |
| 1321 | unlock_page(page); | 1315 | unlock_page(page); |
| 1322 | page_cache_release(page); | 1316 | page_cache_release(page); |
| 1323 | 1317 | ||
| 1324 | if (pos + len > inode->i_size) | 1318 | if (pos + len > inode->i_size) |
| 1325 | vmtruncate(inode, inode->i_size); | 1319 | ext3_truncate(inode); |
| 1326 | return ret ? ret : copied; | 1320 | return ret ? ret : copied; |
| 1327 | } | 1321 | } |
| 1328 | 1322 | ||
| @@ -1358,7 +1352,7 @@ static int ext3_journalled_write_end(struct file *file, | |||
| 1358 | * There may be allocated blocks outside of i_size because | 1352 | * There may be allocated blocks outside of i_size because |
| 1359 | * we failed to copy some data. Prepare for truncate. | 1353 | * we failed to copy some data. Prepare for truncate. |
| 1360 | */ | 1354 | */ |
| 1361 | if (pos + len > inode->i_size) | 1355 | if (pos + len > inode->i_size && ext3_can_truncate(inode)) |
| 1362 | ext3_orphan_add(handle, inode); | 1356 | ext3_orphan_add(handle, inode); |
| 1363 | EXT3_I(inode)->i_state |= EXT3_STATE_JDATA; | 1357 | EXT3_I(inode)->i_state |= EXT3_STATE_JDATA; |
| 1364 | if (inode->i_size > EXT3_I(inode)->i_disksize) { | 1358 | if (inode->i_size > EXT3_I(inode)->i_disksize) { |
| @@ -1375,7 +1369,7 @@ static int ext3_journalled_write_end(struct file *file, | |||
| 1375 | page_cache_release(page); | 1369 | page_cache_release(page); |
| 1376 | 1370 | ||
| 1377 | if (pos + len > inode->i_size) | 1371 | if (pos + len > inode->i_size) |
| 1378 | vmtruncate(inode, inode->i_size); | 1372 | ext3_truncate(inode); |
| 1379 | return ret ? ret : copied; | 1373 | return ret ? ret : copied; |
| 1380 | } | 1374 | } |
| 1381 | 1375 | ||
diff --git a/fs/jbd/journal.c b/fs/jbd/journal.c index 737f7246a4b5..f96f85092d1c 100644 --- a/fs/jbd/journal.c +++ b/fs/jbd/journal.c | |||
| @@ -287,6 +287,7 @@ int journal_write_metadata_buffer(transaction_t *transaction, | |||
| 287 | struct page *new_page; | 287 | struct page *new_page; |
| 288 | unsigned int new_offset; | 288 | unsigned int new_offset; |
| 289 | struct buffer_head *bh_in = jh2bh(jh_in); | 289 | struct buffer_head *bh_in = jh2bh(jh_in); |
| 290 | journal_t *journal = transaction->t_journal; | ||
| 290 | 291 | ||
| 291 | /* | 292 | /* |
| 292 | * The buffer really shouldn't be locked: only the current committing | 293 | * The buffer really shouldn't be locked: only the current committing |
| @@ -300,6 +301,11 @@ int journal_write_metadata_buffer(transaction_t *transaction, | |||
| 300 | J_ASSERT_BH(bh_in, buffer_jbddirty(bh_in)); | 301 | J_ASSERT_BH(bh_in, buffer_jbddirty(bh_in)); |
| 301 | 302 | ||
| 302 | new_bh = alloc_buffer_head(GFP_NOFS|__GFP_NOFAIL); | 303 | new_bh = alloc_buffer_head(GFP_NOFS|__GFP_NOFAIL); |
| 304 | /* keep subsequent assertions sane */ | ||
| 305 | new_bh->b_state = 0; | ||
| 306 | init_buffer(new_bh, NULL, NULL); | ||
| 307 | atomic_set(&new_bh->b_count, 1); | ||
| 308 | new_jh = journal_add_journal_head(new_bh); /* This sleeps */ | ||
| 303 | 309 | ||
| 304 | /* | 310 | /* |
| 305 | * If a new transaction has already done a buffer copy-out, then | 311 | * If a new transaction has already done a buffer copy-out, then |
| @@ -361,14 +367,6 @@ repeat: | |||
| 361 | kunmap_atomic(mapped_data, KM_USER0); | 367 | kunmap_atomic(mapped_data, KM_USER0); |
| 362 | } | 368 | } |
| 363 | 369 | ||
| 364 | /* keep subsequent assertions sane */ | ||
| 365 | new_bh->b_state = 0; | ||
| 366 | init_buffer(new_bh, NULL, NULL); | ||
| 367 | atomic_set(&new_bh->b_count, 1); | ||
| 368 | jbd_unlock_bh_state(bh_in); | ||
| 369 | |||
| 370 | new_jh = journal_add_journal_head(new_bh); /* This sleeps */ | ||
| 371 | |||
| 372 | set_bh_page(new_bh, new_page, new_offset); | 370 | set_bh_page(new_bh, new_page, new_offset); |
| 373 | new_jh->b_transaction = NULL; | 371 | new_jh->b_transaction = NULL; |
| 374 | new_bh->b_size = jh2bh(jh_in)->b_size; | 372 | new_bh->b_size = jh2bh(jh_in)->b_size; |
| @@ -385,7 +383,11 @@ repeat: | |||
| 385 | * copying is moved to the transaction's shadow queue. | 383 | * copying is moved to the transaction's shadow queue. |
| 386 | */ | 384 | */ |
| 387 | JBUFFER_TRACE(jh_in, "file as BJ_Shadow"); | 385 | JBUFFER_TRACE(jh_in, "file as BJ_Shadow"); |
| 388 | journal_file_buffer(jh_in, transaction, BJ_Shadow); | 386 | spin_lock(&journal->j_list_lock); |
| 387 | __journal_file_buffer(jh_in, transaction, BJ_Shadow); | ||
| 388 | spin_unlock(&journal->j_list_lock); | ||
| 389 | jbd_unlock_bh_state(bh_in); | ||
| 390 | |||
| 389 | JBUFFER_TRACE(new_jh, "file as BJ_IO"); | 391 | JBUFFER_TRACE(new_jh, "file as BJ_IO"); |
| 390 | journal_file_buffer(new_jh, transaction, BJ_IO); | 392 | journal_file_buffer(new_jh, transaction, BJ_IO); |
| 391 | 393 | ||
| @@ -848,6 +850,12 @@ static int journal_reset(journal_t *journal) | |||
| 848 | 850 | ||
| 849 | first = be32_to_cpu(sb->s_first); | 851 | first = be32_to_cpu(sb->s_first); |
| 850 | last = be32_to_cpu(sb->s_maxlen); | 852 | last = be32_to_cpu(sb->s_maxlen); |
| 853 | if (first + JFS_MIN_JOURNAL_BLOCKS > last + 1) { | ||
| 854 | printk(KERN_ERR "JBD: Journal too short (blocks %lu-%lu).\n", | ||
| 855 | first, last); | ||
| 856 | journal_fail_superblock(journal); | ||
| 857 | return -EINVAL; | ||
| 858 | } | ||
| 851 | 859 | ||
| 852 | journal->j_first = first; | 860 | journal->j_first = first; |
| 853 | journal->j_last = last; | 861 | journal->j_last = last; |
diff --git a/fs/jbd/transaction.c b/fs/jbd/transaction.c index 73242ba7c7b1..c03ac11f74be 100644 --- a/fs/jbd/transaction.c +++ b/fs/jbd/transaction.c | |||
| @@ -489,34 +489,15 @@ void journal_unlock_updates (journal_t *journal) | |||
| 489 | wake_up(&journal->j_wait_transaction_locked); | 489 | wake_up(&journal->j_wait_transaction_locked); |
| 490 | } | 490 | } |
| 491 | 491 | ||
| 492 | /* | 492 | static void warn_dirty_buffer(struct buffer_head *bh) |
| 493 | * Report any unexpected dirty buffers which turn up. Normally those | ||
| 494 | * indicate an error, but they can occur if the user is running (say) | ||
| 495 | * tune2fs to modify the live filesystem, so we need the option of | ||
| 496 | * continuing as gracefully as possible. # | ||
| 497 | * | ||
| 498 | * The caller should already hold the journal lock and | ||
| 499 | * j_list_lock spinlock: most callers will need those anyway | ||
| 500 | * in order to probe the buffer's journaling state safely. | ||
| 501 | */ | ||
| 502 | static void jbd_unexpected_dirty_buffer(struct journal_head *jh) | ||
| 503 | { | 493 | { |
| 504 | int jlist; | 494 | char b[BDEVNAME_SIZE]; |
| 505 | |||
| 506 | /* If this buffer is one which might reasonably be dirty | ||
| 507 | * --- ie. data, or not part of this journal --- then | ||
| 508 | * we're OK to leave it alone, but otherwise we need to | ||
| 509 | * move the dirty bit to the journal's own internal | ||
| 510 | * JBDDirty bit. */ | ||
| 511 | jlist = jh->b_jlist; | ||
| 512 | 495 | ||
| 513 | if (jlist == BJ_Metadata || jlist == BJ_Reserved || | 496 | printk(KERN_WARNING |
| 514 | jlist == BJ_Shadow || jlist == BJ_Forget) { | 497 | "JBD: Spotted dirty metadata buffer (dev = %s, blocknr = %llu). " |
| 515 | struct buffer_head *bh = jh2bh(jh); | 498 | "There's a risk of filesystem corruption in case of system " |
| 516 | 499 | "crash.\n", | |
| 517 | if (test_clear_buffer_dirty(bh)) | 500 | bdevname(bh->b_bdev, b), (unsigned long long)bh->b_blocknr); |
| 518 | set_buffer_jbddirty(bh); | ||
| 519 | } | ||
| 520 | } | 501 | } |
| 521 | 502 | ||
| 522 | /* | 503 | /* |
| @@ -583,14 +564,16 @@ repeat: | |||
| 583 | if (jh->b_next_transaction) | 564 | if (jh->b_next_transaction) |
| 584 | J_ASSERT_JH(jh, jh->b_next_transaction == | 565 | J_ASSERT_JH(jh, jh->b_next_transaction == |
| 585 | transaction); | 566 | transaction); |
| 567 | warn_dirty_buffer(bh); | ||
| 586 | } | 568 | } |
| 587 | /* | 569 | /* |
| 588 | * In any case we need to clean the dirty flag and we must | 570 | * In any case we need to clean the dirty flag and we must |
| 589 | * do it under the buffer lock to be sure we don't race | 571 | * do it under the buffer lock to be sure we don't race |
| 590 | * with running write-out. | 572 | * with running write-out. |
| 591 | */ | 573 | */ |
| 592 | JBUFFER_TRACE(jh, "Unexpected dirty buffer"); | 574 | JBUFFER_TRACE(jh, "Journalling dirty buffer"); |
| 593 | jbd_unexpected_dirty_buffer(jh); | 575 | clear_buffer_dirty(bh); |
| 576 | set_buffer_jbddirty(bh); | ||
| 594 | } | 577 | } |
| 595 | 578 | ||
| 596 | unlock_buffer(bh); | 579 | unlock_buffer(bh); |
| @@ -826,6 +809,15 @@ int journal_get_create_access(handle_t *handle, struct buffer_head *bh) | |||
| 826 | J_ASSERT_JH(jh, buffer_locked(jh2bh(jh))); | 809 | J_ASSERT_JH(jh, buffer_locked(jh2bh(jh))); |
| 827 | 810 | ||
| 828 | if (jh->b_transaction == NULL) { | 811 | if (jh->b_transaction == NULL) { |
| 812 | /* | ||
| 813 | * Previous journal_forget() could have left the buffer | ||
| 814 | * with jbddirty bit set because it was being committed. When | ||
| 815 | * the commit finished, we've filed the buffer for | ||
| 816 | * checkpointing and marked it dirty. Now we are reallocating | ||
| 817 | * the buffer so the transaction freeing it must have | ||
| 818 | * committed and so it's safe to clear the dirty bit. | ||
| 819 | */ | ||
| 820 | clear_buffer_dirty(jh2bh(jh)); | ||
| 829 | jh->b_transaction = transaction; | 821 | jh->b_transaction = transaction; |
| 830 | 822 | ||
| 831 | /* first access by this transaction */ | 823 | /* first access by this transaction */ |
| @@ -1782,8 +1774,13 @@ static int __dispose_buffer(struct journal_head *jh, transaction_t *transaction) | |||
| 1782 | 1774 | ||
| 1783 | if (jh->b_cp_transaction) { | 1775 | if (jh->b_cp_transaction) { |
| 1784 | JBUFFER_TRACE(jh, "on running+cp transaction"); | 1776 | JBUFFER_TRACE(jh, "on running+cp transaction"); |
| 1777 | /* | ||
| 1778 | * We don't want to write the buffer anymore, clear the | ||
| 1779 | * bit so that we don't confuse checks in | ||
| 1780 | * __journal_file_buffer | ||
| 1781 | */ | ||
| 1782 | clear_buffer_dirty(bh); | ||
| 1785 | __journal_file_buffer(jh, transaction, BJ_Forget); | 1783 | __journal_file_buffer(jh, transaction, BJ_Forget); |
| 1786 | clear_buffer_jbddirty(bh); | ||
| 1787 | may_free = 0; | 1784 | may_free = 0; |
| 1788 | } else { | 1785 | } else { |
| 1789 | JBUFFER_TRACE(jh, "on running transaction"); | 1786 | JBUFFER_TRACE(jh, "on running transaction"); |
| @@ -2041,12 +2038,17 @@ void __journal_file_buffer(struct journal_head *jh, | |||
| 2041 | if (jh->b_transaction && jh->b_jlist == jlist) | 2038 | if (jh->b_transaction && jh->b_jlist == jlist) |
| 2042 | return; | 2039 | return; |
| 2043 | 2040 | ||
| 2044 | /* The following list of buffer states needs to be consistent | ||
| 2045 | * with __jbd_unexpected_dirty_buffer()'s handling of dirty | ||
| 2046 | * state. */ | ||
| 2047 | |||
| 2048 | if (jlist == BJ_Metadata || jlist == BJ_Reserved || | 2041 | if (jlist == BJ_Metadata || jlist == BJ_Reserved || |
| 2049 | jlist == BJ_Shadow || jlist == BJ_Forget) { | 2042 | jlist == BJ_Shadow || jlist == BJ_Forget) { |
| 2043 | /* | ||
| 2044 | * For metadata buffers, we track dirty bit in buffer_jbddirty | ||
| 2045 | * instead of buffer_dirty. We should not see a dirty bit set | ||
| 2046 | * here because we clear it in do_get_write_access but e.g. | ||
| 2047 | * tune2fs can modify the sb and set the dirty bit at any time | ||
| 2048 | * so we try to gracefully handle that. | ||
| 2049 | */ | ||
| 2050 | if (buffer_dirty(bh)) | ||
| 2051 | warn_dirty_buffer(bh); | ||
| 2050 | if (test_clear_buffer_dirty(bh) || | 2052 | if (test_clear_buffer_dirty(bh) || |
| 2051 | test_clear_buffer_jbddirty(bh)) | 2053 | test_clear_buffer_jbddirty(bh)) |
| 2052 | was_dirty = 1; | 2054 | was_dirty = 1; |
diff --git a/fs/jfs/acl.c b/fs/jfs/acl.c index 91fa3ad6e8c2..a29c7c3e3fb8 100644 --- a/fs/jfs/acl.c +++ b/fs/jfs/acl.c | |||
| @@ -67,10 +67,8 @@ static struct posix_acl *jfs_get_acl(struct inode *inode, int type) | |||
| 67 | acl = posix_acl_from_xattr(value, size); | 67 | acl = posix_acl_from_xattr(value, size); |
| 68 | } | 68 | } |
| 69 | kfree(value); | 69 | kfree(value); |
| 70 | if (!IS_ERR(acl)) { | 70 | if (!IS_ERR(acl)) |
| 71 | set_cached_acl(inode, type, acl); | 71 | set_cached_acl(inode, type, acl); |
| 72 | posix_acl_release(acl); | ||
| 73 | } | ||
| 74 | return acl; | 72 | return acl; |
| 75 | } | 73 | } |
| 76 | 74 | ||
diff --git a/include/asm-generic/4level-fixup.h b/include/asm-generic/4level-fixup.h index 9d40e879f99e..77ff547730af 100644 --- a/include/asm-generic/4level-fixup.h +++ b/include/asm-generic/4level-fixup.h | |||
| @@ -27,9 +27,9 @@ | |||
| 27 | #define pud_page_vaddr(pud) pgd_page_vaddr(pud) | 27 | #define pud_page_vaddr(pud) pgd_page_vaddr(pud) |
| 28 | 28 | ||
| 29 | #undef pud_free_tlb | 29 | #undef pud_free_tlb |
| 30 | #define pud_free_tlb(tlb, x) do { } while (0) | 30 | #define pud_free_tlb(tlb, x, addr) do { } while (0) |
| 31 | #define pud_free(mm, x) do { } while (0) | 31 | #define pud_free(mm, x) do { } while (0) |
| 32 | #define __pud_free_tlb(tlb, x) do { } while (0) | 32 | #define __pud_free_tlb(tlb, x, addr) do { } while (0) |
| 33 | 33 | ||
| 34 | #undef pud_addr_end | 34 | #undef pud_addr_end |
| 35 | #define pud_addr_end(addr, end) (end) | 35 | #define pud_addr_end(addr, end) (end) |
diff --git a/include/asm-generic/pgtable-nopmd.h b/include/asm-generic/pgtable-nopmd.h index a7cdc48e8b78..725612b793ce 100644 --- a/include/asm-generic/pgtable-nopmd.h +++ b/include/asm-generic/pgtable-nopmd.h | |||
| @@ -59,7 +59,7 @@ static inline pmd_t * pmd_offset(pud_t * pud, unsigned long address) | |||
| 59 | static inline void pmd_free(struct mm_struct *mm, pmd_t *pmd) | 59 | static inline void pmd_free(struct mm_struct *mm, pmd_t *pmd) |
| 60 | { | 60 | { |
| 61 | } | 61 | } |
| 62 | #define __pmd_free_tlb(tlb, x) do { } while (0) | 62 | #define __pmd_free_tlb(tlb, x, a) do { } while (0) |
| 63 | 63 | ||
| 64 | #undef pmd_addr_end | 64 | #undef pmd_addr_end |
| 65 | #define pmd_addr_end(addr, end) (end) | 65 | #define pmd_addr_end(addr, end) (end) |
diff --git a/include/asm-generic/pgtable-nopud.h b/include/asm-generic/pgtable-nopud.h index 87cf449a6df3..810431d8351b 100644 --- a/include/asm-generic/pgtable-nopud.h +++ b/include/asm-generic/pgtable-nopud.h | |||
| @@ -52,7 +52,7 @@ static inline pud_t * pud_offset(pgd_t * pgd, unsigned long address) | |||
| 52 | */ | 52 | */ |
| 53 | #define pud_alloc_one(mm, address) NULL | 53 | #define pud_alloc_one(mm, address) NULL |
| 54 | #define pud_free(mm, x) do { } while (0) | 54 | #define pud_free(mm, x) do { } while (0) |
| 55 | #define __pud_free_tlb(tlb, x) do { } while (0) | 55 | #define __pud_free_tlb(tlb, x, a) do { } while (0) |
| 56 | 56 | ||
| 57 | #undef pud_addr_end | 57 | #undef pud_addr_end |
| 58 | #define pud_addr_end(addr, end) (end) | 58 | #define pud_addr_end(addr, end) (end) |
diff --git a/include/asm-generic/tlb.h b/include/asm-generic/tlb.h index f490e43a90b9..e43f9766259f 100644 --- a/include/asm-generic/tlb.h +++ b/include/asm-generic/tlb.h | |||
| @@ -123,24 +123,24 @@ static inline void tlb_remove_page(struct mmu_gather *tlb, struct page *page) | |||
| 123 | __tlb_remove_tlb_entry(tlb, ptep, address); \ | 123 | __tlb_remove_tlb_entry(tlb, ptep, address); \ |
| 124 | } while (0) | 124 | } while (0) |
| 125 | 125 | ||
| 126 | #define pte_free_tlb(tlb, ptep) \ | 126 | #define pte_free_tlb(tlb, ptep, address) \ |
| 127 | do { \ | 127 | do { \ |
| 128 | tlb->need_flush = 1; \ | 128 | tlb->need_flush = 1; \ |
| 129 | __pte_free_tlb(tlb, ptep); \ | 129 | __pte_free_tlb(tlb, ptep, address); \ |
| 130 | } while (0) | 130 | } while (0) |
| 131 | 131 | ||
| 132 | #ifndef __ARCH_HAS_4LEVEL_HACK | 132 | #ifndef __ARCH_HAS_4LEVEL_HACK |
| 133 | #define pud_free_tlb(tlb, pudp) \ | 133 | #define pud_free_tlb(tlb, pudp, address) \ |
| 134 | do { \ | 134 | do { \ |
| 135 | tlb->need_flush = 1; \ | 135 | tlb->need_flush = 1; \ |
| 136 | __pud_free_tlb(tlb, pudp); \ | 136 | __pud_free_tlb(tlb, pudp, address); \ |
| 137 | } while (0) | 137 | } while (0) |
| 138 | #endif | 138 | #endif |
| 139 | 139 | ||
| 140 | #define pmd_free_tlb(tlb, pmdp) \ | 140 | #define pmd_free_tlb(tlb, pmdp, address) \ |
| 141 | do { \ | 141 | do { \ |
| 142 | tlb->need_flush = 1; \ | 142 | tlb->need_flush = 1; \ |
| 143 | __pmd_free_tlb(tlb, pmdp); \ | 143 | __pmd_free_tlb(tlb, pmdp, address); \ |
| 144 | } while (0) | 144 | } while (0) |
| 145 | 145 | ||
| 146 | #define tlb_migrate_finish(mm) do {} while (0) | 146 | #define tlb_migrate_finish(mm) do {} while (0) |
diff --git a/include/linux/ext3_fs.h b/include/linux/ext3_fs.h index 634a5e5aba3e..7499b3667798 100644 --- a/include/linux/ext3_fs.h +++ b/include/linux/ext3_fs.h | |||
| @@ -874,7 +874,7 @@ struct buffer_head * ext3_getblk (handle_t *, struct inode *, long, int, int *); | |||
| 874 | struct buffer_head * ext3_bread (handle_t *, struct inode *, int, int, int *); | 874 | struct buffer_head * ext3_bread (handle_t *, struct inode *, int, int, int *); |
| 875 | int ext3_get_blocks_handle(handle_t *handle, struct inode *inode, | 875 | int ext3_get_blocks_handle(handle_t *handle, struct inode *inode, |
| 876 | sector_t iblock, unsigned long maxblocks, struct buffer_head *bh_result, | 876 | sector_t iblock, unsigned long maxblocks, struct buffer_head *bh_result, |
| 877 | int create, int extend_disksize); | 877 | int create); |
| 878 | 878 | ||
| 879 | extern struct inode *ext3_iget(struct super_block *, unsigned long); | 879 | extern struct inode *ext3_iget(struct super_block *, unsigned long); |
| 880 | extern int ext3_write_inode (struct inode *, int); | 880 | extern int ext3_write_inode (struct inode *, int); |
diff --git a/kernel/kthread.c b/kernel/kthread.c index 9b1a7de26979..eb8751aa0418 100644 --- a/kernel/kthread.c +++ b/kernel/kthread.c | |||
| @@ -180,10 +180,12 @@ EXPORT_SYMBOL(kthread_bind); | |||
| 180 | * @k: thread created by kthread_create(). | 180 | * @k: thread created by kthread_create(). |
| 181 | * | 181 | * |
| 182 | * Sets kthread_should_stop() for @k to return true, wakes it, and | 182 | * Sets kthread_should_stop() for @k to return true, wakes it, and |
| 183 | * waits for it to exit. Your threadfn() must not call do_exit() | 183 | * waits for it to exit. This can also be called after kthread_create() |
| 184 | * itself if you use this function! This can also be called after | 184 | * instead of calling wake_up_process(): the thread will exit without |
| 185 | * kthread_create() instead of calling wake_up_process(): the thread | 185 | * calling threadfn(). |
| 186 | * will exit without calling threadfn(). | 186 | * |
| 187 | * If threadfn() may call do_exit() itself, the caller must ensure | ||
| 188 | * task_struct can't go away. | ||
| 187 | * | 189 | * |
| 188 | * Returns the result of threadfn(), or %-EINTR if wake_up_process() | 190 | * Returns the result of threadfn(), or %-EINTR if wake_up_process() |
| 189 | * was never called. | 191 | * was never called. |
diff --git a/kernel/module.c b/kernel/module.c index 0a049837008e..fd1411403558 100644 --- a/kernel/module.c +++ b/kernel/module.c | |||
| @@ -1068,7 +1068,8 @@ static inline int check_modstruct_version(Elf_Shdr *sechdrs, | |||
| 1068 | { | 1068 | { |
| 1069 | const unsigned long *crc; | 1069 | const unsigned long *crc; |
| 1070 | 1070 | ||
| 1071 | if (!find_symbol("module_layout", NULL, &crc, true, false)) | 1071 | if (!find_symbol(MODULE_SYMBOL_PREFIX "module_layout", NULL, |
| 1072 | &crc, true, false)) | ||
| 1072 | BUG(); | 1073 | BUG(); |
| 1073 | return check_version(sechdrs, versindex, "module_layout", mod, crc); | 1074 | return check_version(sechdrs, versindex, "module_layout", mod, crc); |
| 1074 | } | 1075 | } |
diff --git a/mm/memory.c b/mm/memory.c index 65216194eb8d..aede2ce3aba4 100644 --- a/mm/memory.c +++ b/mm/memory.c | |||
| @@ -135,11 +135,12 @@ void pmd_clear_bad(pmd_t *pmd) | |||
| 135 | * Note: this doesn't free the actual pages themselves. That | 135 | * Note: this doesn't free the actual pages themselves. That |
| 136 | * has been handled earlier when unmapping all the memory regions. | 136 | * has been handled earlier when unmapping all the memory regions. |
| 137 | */ | 137 | */ |
| 138 | static void free_pte_range(struct mmu_gather *tlb, pmd_t *pmd) | 138 | static void free_pte_range(struct mmu_gather *tlb, pmd_t *pmd, |
| 139 | unsigned long addr) | ||
| 139 | { | 140 | { |
| 140 | pgtable_t token = pmd_pgtable(*pmd); | 141 | pgtable_t token = pmd_pgtable(*pmd); |
| 141 | pmd_clear(pmd); | 142 | pmd_clear(pmd); |
| 142 | pte_free_tlb(tlb, token); | 143 | pte_free_tlb(tlb, token, addr); |
| 143 | tlb->mm->nr_ptes--; | 144 | tlb->mm->nr_ptes--; |
| 144 | } | 145 | } |
| 145 | 146 | ||
| @@ -157,7 +158,7 @@ static inline void free_pmd_range(struct mmu_gather *tlb, pud_t *pud, | |||
| 157 | next = pmd_addr_end(addr, end); | 158 | next = pmd_addr_end(addr, end); |
| 158 | if (pmd_none_or_clear_bad(pmd)) | 159 | if (pmd_none_or_clear_bad(pmd)) |
| 159 | continue; | 160 | continue; |
| 160 | free_pte_range(tlb, pmd); | 161 | free_pte_range(tlb, pmd, addr); |
| 161 | } while (pmd++, addr = next, addr != end); | 162 | } while (pmd++, addr = next, addr != end); |
| 162 | 163 | ||
| 163 | start &= PUD_MASK; | 164 | start &= PUD_MASK; |
| @@ -173,7 +174,7 @@ static inline void free_pmd_range(struct mmu_gather *tlb, pud_t *pud, | |||
| 173 | 174 | ||
| 174 | pmd = pmd_offset(pud, start); | 175 | pmd = pmd_offset(pud, start); |
| 175 | pud_clear(pud); | 176 | pud_clear(pud); |
| 176 | pmd_free_tlb(tlb, pmd); | 177 | pmd_free_tlb(tlb, pmd, start); |
| 177 | } | 178 | } |
| 178 | 179 | ||
| 179 | static inline void free_pud_range(struct mmu_gather *tlb, pgd_t *pgd, | 180 | static inline void free_pud_range(struct mmu_gather *tlb, pgd_t *pgd, |
| @@ -206,7 +207,7 @@ static inline void free_pud_range(struct mmu_gather *tlb, pgd_t *pgd, | |||
| 206 | 207 | ||
| 207 | pud = pud_offset(pgd, start); | 208 | pud = pud_offset(pgd, start); |
| 208 | pgd_clear(pgd); | 209 | pgd_clear(pgd); |
| 209 | pud_free_tlb(tlb, pud); | 210 | pud_free_tlb(tlb, pud, start); |
| 210 | } | 211 | } |
| 211 | 212 | ||
| 212 | /* | 213 | /* |
