Commit-ID:  d4925e00d59698a201231cf99dce47d8b922bb34
Gitweb:     http://git.kernel.org/tip/d4925e00d59698a201231cf99dce47d8b922bb34
Author:     Dave Hansen <[email protected]>
AuthorDate: Fri, 12 Feb 2016 13:02:16 -0800
Committer:  Ingo Molnar <[email protected]>
CommitDate: Thu, 18 Feb 2016 09:32:43 +0100

mm/gup: Factor out VMA fault permission checking

This code matches a fault condition up with the VMA and ensures
that the VMA allows the fault to be handled instead of just
erroring out.

We will be extending this in a moment to comprehend protection
keys.

Signed-off-by: Dave Hansen <[email protected]>
Reviewed-by: Thomas Gleixner <[email protected]>
Cc: Andrew Morton <[email protected]>
Cc: Andy Lutomirski <[email protected]>
Cc: Aneesh Kumar K.V <[email protected]>
Cc: Borislav Petkov <[email protected]>
Cc: Brian Gerst <[email protected]>
Cc: Dan Williams <[email protected]>
Cc: Dave Hansen <[email protected]>
Cc: Denys Vlasenko <[email protected]>
Cc: Dominik Dingel <[email protected]>
Cc: Eric B Munson <[email protected]>
Cc: H. Peter Anvin <[email protected]>
Cc: Jason Low <[email protected]>
Cc: Kirill A. Shutemov <[email protected]>
Cc: Linus Torvalds <[email protected]>
Cc: Peter Zijlstra <[email protected]>
Cc: Rik van Riel <[email protected]>
Cc: Sasha Levin <[email protected]>
Cc: [email protected]
Cc: [email protected]
Link: http://lkml.kernel.org/r/[email protected]
Signed-off-by: Ingo Molnar <[email protected]>
---
 mm/gup.c | 16 +++++++++++++---
 1 file changed, 13 insertions(+), 3 deletions(-)

diff --git a/mm/gup.c b/mm/gup.c
index de24ef4..b935c2c 100644
--- a/mm/gup.c
+++ b/mm/gup.c
@@ -610,6 +610,18 @@ next_page:
 }
 EXPORT_SYMBOL(__get_user_pages);
 
+bool vma_permits_fault(struct vm_area_struct *vma, unsigned int fault_flags)
+{
+       vm_flags_t vm_flags;
+
+       vm_flags = (fault_flags & FAULT_FLAG_WRITE) ? VM_WRITE : VM_READ;
+
+       if (!(vm_flags & vma->vm_flags))
+               return false;
+
+       return true;
+}
+
 /*
  * fixup_user_fault() - manually resolve a user page fault
  * @tsk:       the task_struct to use for page fault accounting, or
@@ -645,7 +657,6 @@ int fixup_user_fault(struct task_struct *tsk, struct 
mm_struct *mm,
                     bool *unlocked)
 {
        struct vm_area_struct *vma;
-       vm_flags_t vm_flags;
        int ret, major = 0;
 
        if (unlocked)
@@ -656,8 +667,7 @@ retry:
        if (!vma || address < vma->vm_start)
                return -EFAULT;
 
-       vm_flags = (fault_flags & FAULT_FLAG_WRITE) ? VM_WRITE : VM_READ;
-       if (!(vm_flags & vma->vm_flags))
+       if (!vma_permits_fault(vma, fault_flags))
                return -EFAULT;
 
        ret = handle_mm_fault(mm, vma, address, fault_flags);

Reply via email to