diff options
author | Stephen Wilson <wilsons@start.ca> | 2011-03-13 15:49:18 -0400 |
---|---|---|
committer | Al Viro <viro@zeniv.linux.org.uk> | 2011-03-23 16:36:56 -0400 |
commit | e7f22e207bacdba5b73f2893a3abe935a5373e2e (patch) | |
tree | 02e9f01788742db409587475a0aa10f3a0347e38 /mm | |
parent | cae5d39032acf26c265f6b1dc73d7ce6ff4bc387 (diff) |
mm: use mm_struct to resolve gate vma's in __get_user_pages
We now check if a requested user page overlaps a gate vma using the supplied mm
instead of the supplied task. The given task is now used solely for accounting
purposes and may be NULL.
Signed-off-by: Stephen Wilson <wilsons@start.ca>
Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
Diffstat (limited to 'mm')
-rw-r--r-- | mm/memory.c | 18 |
1 files changed, 11 insertions, 7 deletions
diff --git a/mm/memory.c b/mm/memory.c index 5f5b5de5a40e..5f585b65d734 100644 --- a/mm/memory.c +++ b/mm/memory.c | |||
@@ -1486,9 +1486,9 @@ int __get_user_pages(struct task_struct *tsk, struct mm_struct *mm, | |||
1486 | struct vm_area_struct *vma; | 1486 | struct vm_area_struct *vma; |
1487 | 1487 | ||
1488 | vma = find_extend_vma(mm, start); | 1488 | vma = find_extend_vma(mm, start); |
1489 | if (!vma && in_gate_area(tsk->mm, start)) { | 1489 | if (!vma && in_gate_area(mm, start)) { |
1490 | unsigned long pg = start & PAGE_MASK; | 1490 | unsigned long pg = start & PAGE_MASK; |
1491 | struct vm_area_struct *gate_vma = get_gate_vma(tsk->mm); | 1491 | struct vm_area_struct *gate_vma = get_gate_vma(mm); |
1492 | pgd_t *pgd; | 1492 | pgd_t *pgd; |
1493 | pud_t *pud; | 1493 | pud_t *pud; |
1494 | pmd_t *pmd; | 1494 | pmd_t *pmd; |
@@ -1589,10 +1589,13 @@ int __get_user_pages(struct task_struct *tsk, struct mm_struct *mm, | |||
1589 | return i ? i : -EFAULT; | 1589 | return i ? i : -EFAULT; |
1590 | BUG(); | 1590 | BUG(); |
1591 | } | 1591 | } |
1592 | if (ret & VM_FAULT_MAJOR) | 1592 | |
1593 | tsk->maj_flt++; | 1593 | if (tsk) { |
1594 | else | 1594 | if (ret & VM_FAULT_MAJOR) |
1595 | tsk->min_flt++; | 1595 | tsk->maj_flt++; |
1596 | else | ||
1597 | tsk->min_flt++; | ||
1598 | } | ||
1596 | 1599 | ||
1597 | if (ret & VM_FAULT_RETRY) { | 1600 | if (ret & VM_FAULT_RETRY) { |
1598 | *nonblocking = 0; | 1601 | *nonblocking = 0; |
@@ -1638,7 +1641,8 @@ EXPORT_SYMBOL(__get_user_pages); | |||
1638 | 1641 | ||
1639 | /** | 1642 | /** |
1640 | * get_user_pages() - pin user pages in memory | 1643 | * get_user_pages() - pin user pages in memory |
1641 | * @tsk: task_struct of target task | 1644 | * @tsk: the task_struct to use for page fault accounting, or |
1645 | * NULL if faults are not to be recorded. | ||
1642 | * @mm: mm_struct of target mm | 1646 | * @mm: mm_struct of target mm |
1643 | * @start: starting user address | 1647 | * @start: starting user address |
1644 | * @nr_pages: number of pages from start to pin | 1648 | * @nr_pages: number of pages from start to pin |