Skip to content

Commit 01d1e0e

Browse files
Matthew Wilcox (Oracle)akpm00
authored andcommitted
mm: convert __do_fault() to use a folio
Convert vmf->page to a folio as soon as we're going to use it. This fixes a bug if the fault handler returns a tail page with hardware poison; tail pages have an invalid page->index, so we would fail to unmap the page from the page tables. We actually have to unmap the entire folio (or mapping_evict_folio() will fail), so use unmap_mapping_folio() instead. This also saves various calls to compound_head() hidden in lock_page(), put_page(), etc. Link: https://lkml.kernel.org/r/[email protected] Fixes: 793917d ("mm/readahead: Add large folio readahead") Signed-off-by: Matthew Wilcox (Oracle) <[email protected]> Cc: Naoya Horiguchi <[email protected]> Signed-off-by: Andrew Morton <[email protected]>
1 parent 1e12cbb commit 01d1e0e

File tree

1 file changed

+10
-10
lines changed

1 file changed

+10
-10
lines changed

mm/memory.c

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -4245,6 +4245,7 @@ static vm_fault_t do_anonymous_page(struct vm_fault *vmf)
42454245
static vm_fault_t __do_fault(struct vm_fault *vmf)
42464246
{
42474247
struct vm_area_struct *vma = vmf->vma;
4248+
struct folio *folio;
42484249
vm_fault_t ret;
42494250

42504251
/*
@@ -4273,27 +4274,26 @@ static vm_fault_t __do_fault(struct vm_fault *vmf)
42734274
VM_FAULT_DONE_COW)))
42744275
return ret;
42754276

4277+
folio = page_folio(vmf->page);
42764278
if (unlikely(PageHWPoison(vmf->page))) {
4277-
struct page *page = vmf->page;
42784279
vm_fault_t poisonret = VM_FAULT_HWPOISON;
42794280
if (ret & VM_FAULT_LOCKED) {
4280-
if (page_mapped(page))
4281-
unmap_mapping_pages(page_mapping(page),
4282-
page->index, 1, false);
4283-
/* Retry if a clean page was removed from the cache. */
4284-
if (invalidate_inode_page(page))
4281+
if (page_mapped(vmf->page))
4282+
unmap_mapping_folio(folio);
4283+
/* Retry if a clean folio was removed from the cache. */
4284+
if (mapping_evict_folio(folio->mapping, folio))
42854285
poisonret = VM_FAULT_NOPAGE;
4286-
unlock_page(page);
4286+
folio_unlock(folio);
42874287
}
4288-
put_page(page);
4288+
folio_put(folio);
42894289
vmf->page = NULL;
42904290
return poisonret;
42914291
}
42924292

42934293
if (unlikely(!(ret & VM_FAULT_LOCKED)))
4294-
lock_page(vmf->page);
4294+
folio_lock(folio);
42954295
else
4296-
VM_BUG_ON_PAGE(!PageLocked(vmf->page), vmf->page);
4296+
VM_BUG_ON_PAGE(!folio_test_locked(folio), vmf->page);
42974297

42984298
return ret;
42994299
}

0 commit comments

Comments
 (0)