|
@@ -381,7 +381,13 @@ vma_address(struct page *page, struct vm_area_struct *vma)
|
|
unsigned long page_address_in_vma(struct page *page, struct vm_area_struct *vma)
|
|
unsigned long page_address_in_vma(struct page *page, struct vm_area_struct *vma)
|
|
{
|
|
{
|
|
if (PageAnon(page)) {
|
|
if (PageAnon(page)) {
|
|
- if (vma->anon_vma->root != page_anon_vma(page)->root)
|
|
|
|
|
|
+ struct anon_vma *page__anon_vma = page_anon_vma(page);
|
|
|
|
+ /*
|
|
|
|
+ * Note: swapoff's unuse_vma() is more efficient with this
|
|
|
|
+ * check, and needs it to match anon_vma when KSM is active.
|
|
|
|
+ */
|
|
|
|
+ if (!vma->anon_vma || !page__anon_vma ||
|
|
|
|
+ vma->anon_vma->root != page__anon_vma->root)
|
|
return -EFAULT;
|
|
return -EFAULT;
|
|
} else if (page->mapping && !(vma->vm_flags & VM_NONLINEAR)) {
|
|
} else if (page->mapping && !(vma->vm_flags & VM_NONLINEAR)) {
|
|
if (!vma->vm_file ||
|
|
if (!vma->vm_file ||
|