aboutsummaryrefslogtreecommitdiffstats
path: root/mm/filemap_xip.c
diff options
context:
space:
mode:
Diffstat (limited to 'mm/filemap_xip.c')
-rw-r--r--mm/filemap_xip.c22
1 files changed, 12 insertions, 10 deletions
diff --git a/mm/filemap_xip.c b/mm/filemap_xip.c
index 8c199f537732..9cf687e4a29a 100644
--- a/mm/filemap_xip.c
+++ b/mm/filemap_xip.c
@@ -174,6 +174,8 @@ __xip_unmap (struct address_space * mapping,
174 unsigned long address; 174 unsigned long address;
175 pte_t *pte; 175 pte_t *pte;
176 pte_t pteval; 176 pte_t pteval;
177 spinlock_t *ptl;
178 struct page *page;
177 179
178 spin_lock(&mapping->i_mmap_lock); 180 spin_lock(&mapping->i_mmap_lock);
179 vma_prio_tree_foreach(vma, &iter, &mapping->i_mmap, pgoff, pgoff) { 181 vma_prio_tree_foreach(vma, &iter, &mapping->i_mmap, pgoff, pgoff) {
@@ -181,19 +183,17 @@ __xip_unmap (struct address_space * mapping,
181 address = vma->vm_start + 183 address = vma->vm_start +
182 ((pgoff - vma->vm_pgoff) << PAGE_SHIFT); 184 ((pgoff - vma->vm_pgoff) << PAGE_SHIFT);
183 BUG_ON(address < vma->vm_start || address >= vma->vm_end); 185 BUG_ON(address < vma->vm_start || address >= vma->vm_end);
184 /* 186 page = ZERO_PAGE(address);
185 * We need the page_table_lock to protect us from page faults, 187 pte = page_check_address(page, mm, address, &ptl);
186 * munmap, fork, etc... 188 if (pte) {
187 */
188 pte = page_check_address(ZERO_PAGE(address), mm,
189 address);
190 if (!IS_ERR(pte)) {
191 /* Nuke the page table entry. */ 189 /* Nuke the page table entry. */
192 flush_cache_page(vma, address, pte_pfn(*pte)); 190 flush_cache_page(vma, address, pte_pfn(*pte));
193 pteval = ptep_clear_flush(vma, address, pte); 191 pteval = ptep_clear_flush(vma, address, pte);
192 page_remove_rmap(page);
193 dec_mm_counter(mm, file_rss);
194 BUG_ON(pte_dirty(pteval)); 194 BUG_ON(pte_dirty(pteval));
195 pte_unmap(pte); 195 pte_unmap_unlock(pte, ptl);
196 spin_unlock(&mm->page_table_lock); 196 page_cache_release(page);
197 } 197 }
198 } 198 }
199 spin_unlock(&mapping->i_mmap_lock); 199 spin_unlock(&mapping->i_mmap_lock);
@@ -228,7 +228,7 @@ xip_file_nopage(struct vm_area_struct * area,
228 228
229 page = mapping->a_ops->get_xip_page(mapping, pgoff*(PAGE_SIZE/512), 0); 229 page = mapping->a_ops->get_xip_page(mapping, pgoff*(PAGE_SIZE/512), 0);
230 if (!IS_ERR(page)) { 230 if (!IS_ERR(page)) {
231 return page; 231 goto out;
232 } 232 }
233 if (PTR_ERR(page) != -ENODATA) 233 if (PTR_ERR(page) != -ENODATA)
234 return NULL; 234 return NULL;
@@ -249,6 +249,8 @@ xip_file_nopage(struct vm_area_struct * area,
249 page = ZERO_PAGE(address); 249 page = ZERO_PAGE(address);
250 } 250 }
251 251
252out:
253 page_cache_get(page);
252 return page; 254 return page;
253} 255}
254 256