As recommended by Nick Piggin. Signed-off-by: Wu Fengguang --- include/linux/mm.h | 1 + mm/memory-failure.c | 23 +++++++++++++---------- mm/truncate.c | 3 +-- 3 files changed, 15 insertions(+), 12 deletions(-) --- sound-2.6.orig/mm/memory-failure.c +++ sound-2.6/mm/memory-failure.c @@ -113,6 +113,10 @@ static int me_pagecache_clean(struct pag if (!isolate_lru_page(p)) page_cache_release(p); + mapping = page_mapping(p); + if (mapping == NULL) + return RECOVERED; + /* * Now truncate the page in the page cache. This is really * more like a "temporary hole punch" @@ -120,20 +124,19 @@ static int me_pagecache_clean(struct pag * has a reference, because it could be file system metadata * and that's not safe to truncate. */ - mapping = page_mapping(p); - if (mapping && S_ISBLK(mapping->host->i_mode) && page_count(p) > 1) { + if (!S_ISREG(mapping->host->i_mode) && + !invalidate_complete_page(mapping, p)) { printk(KERN_ERR - "MCE %#lx: page looks like a unsupported file system metadata page\n", + "MCE %#lx: failed to invalidate metadata page\n", pfn); return FAILED; } - if (mapping) { - truncate_inode_page(mapping, p); - if (page_has_private(p) && !try_to_release_page(p, GFP_NOIO)) { - pr_debug(KERN_ERR "MCE %#lx: failed to release buffers\n", - pfn); - return FAILED; - } + + truncate_inode_page(mapping, p); + if (page_has_private(p) && !try_to_release_page(p, GFP_NOIO)) { + pr_debug(KERN_ERR "MCE %#lx: failed to release buffers\n", + pfn); + return FAILED; } return RECOVERED; } --- sound-2.6.orig/include/linux/mm.h +++ sound-2.6/include/linux/mm.h @@ -817,6 +817,7 @@ extern int vmtruncate(struct inode * ino extern int vmtruncate_range(struct inode * inode, loff_t offset, loff_t end); void truncate_inode_page(struct address_space *mapping, struct page *page); +int invalidate_complete_page(struct address_space *mapping, struct page *page); #ifdef CONFIG_MMU extern int handle_mm_fault(struct mm_struct *mm, struct vm_area_struct *vma, --- sound-2.6.orig/mm/truncate.c +++ sound-2.6/mm/truncate.c @@ -118,8 +118,7 @@ truncate_complete_page(struct address_sp * * Returns non-zero if the page was successfully invalidated. */ -static int -invalidate_complete_page(struct address_space *mapping, struct page *page) +int invalidate_complete_page(struct address_space *mapping, struct page *page) { int ret; -- -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/