|
@@ -325,9 +325,37 @@ void kvfree(const void *addr)
|
|
|
}
|
|
|
EXPORT_SYMBOL(kvfree);
|
|
|
|
|
|
+static inline void *__page_rmapping(struct page *page)
|
|
|
+{
|
|
|
+ unsigned long mapping;
|
|
|
+
|
|
|
+ mapping = (unsigned long)page->mapping;
|
|
|
+ mapping &= ~PAGE_MAPPING_FLAGS;
|
|
|
+
|
|
|
+ return (void *)mapping;
|
|
|
+}
|
|
|
+
|
|
|
+/* Neutral page->mapping pointer to address_space or anon_vma or other */
|
|
|
+void *page_rmapping(struct page *page)
|
|
|
+{
|
|
|
+ page = compound_head(page);
|
|
|
+ return __page_rmapping(page);
|
|
|
+}
|
|
|
+
|
|
|
+struct anon_vma *page_anon_vma(struct page *page)
|
|
|
+{
|
|
|
+ unsigned long mapping;
|
|
|
+
|
|
|
+ page = compound_head(page);
|
|
|
+ mapping = (unsigned long)page->mapping;
|
|
|
+ if ((mapping & PAGE_MAPPING_FLAGS) != PAGE_MAPPING_ANON)
|
|
|
+ return NULL;
|
|
|
+ return __page_rmapping(page);
|
|
|
+}
|
|
|
+
|
|
|
struct address_space *page_mapping(struct page *page)
|
|
|
{
|
|
|
- struct address_space *mapping = page->mapping;
|
|
|
+ unsigned long mapping;
|
|
|
|
|
|
/* This happens if someone calls flush_dcache_page on slab page */
|
|
|
if (unlikely(PageSlab(page)))
|
|
@@ -337,10 +365,13 @@ struct address_space *page_mapping(struct page *page)
|
|
|
swp_entry_t entry;
|
|
|
|
|
|
entry.val = page_private(page);
|
|
|
- mapping = swap_address_space(entry);
|
|
|
- } else if ((unsigned long)mapping & PAGE_MAPPING_ANON)
|
|
|
- mapping = NULL;
|
|
|
- return mapping;
|
|
|
+ return swap_address_space(entry);
|
|
|
+ }
|
|
|
+
|
|
|
+ mapping = (unsigned long)page->mapping;
|
|
|
+ if (mapping & PAGE_MAPPING_FLAGS)
|
|
|
+ return NULL;
|
|
|
+ return page->mapping;
|
|
|
}
|
|
|
|
|
|
int overcommit_ratio_handler(struct ctl_table *table, int write,
|