aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/linux/hugetlb.h2
-rw-r--r--mm/hugetlb.c27
2 files changed, 20 insertions, 9 deletions
diff --git a/include/linux/hugetlb.h b/include/linux/hugetlb.h
index 35afca1692fb..1222fb07a746 100644
--- a/include/linux/hugetlb.h
+++ b/include/linux/hugetlb.h
@@ -333,6 +333,8 @@ struct huge_bootmem_page {
333struct page *alloc_huge_page_node(struct hstate *h, int nid); 333struct page *alloc_huge_page_node(struct hstate *h, int nid);
334struct page *alloc_huge_page_noerr(struct vm_area_struct *vma, 334struct page *alloc_huge_page_noerr(struct vm_area_struct *vma,
335 unsigned long addr, int avoid_reserve); 335 unsigned long addr, int avoid_reserve);
336int huge_add_to_page_cache(struct page *page, struct address_space *mapping,
337 pgoff_t idx);
336 338
337/* arch callback */ 339/* arch callback */
338int __init alloc_bootmem_huge_page(struct hstate *h); 340int __init alloc_bootmem_huge_page(struct hstate *h);
diff --git a/mm/hugetlb.c b/mm/hugetlb.c
index 114ad6ce7030..d45eacc5653e 100644
--- a/mm/hugetlb.c
+++ b/mm/hugetlb.c
@@ -3375,6 +3375,23 @@ static bool hugetlbfs_pagecache_present(struct hstate *h,
3375 return page != NULL; 3375 return page != NULL;
3376} 3376}
3377 3377
3378int huge_add_to_page_cache(struct page *page, struct address_space *mapping,
3379 pgoff_t idx)
3380{
3381 struct inode *inode = mapping->host;
3382 struct hstate *h = hstate_inode(inode);
3383 int err = add_to_page_cache(page, mapping, idx, GFP_KERNEL);
3384
3385 if (err)
3386 return err;
3387 ClearPagePrivate(page);
3388
3389 spin_lock(&inode->i_lock);
3390 inode->i_blocks += blocks_per_huge_page(h);
3391 spin_unlock(&inode->i_lock);
3392 return 0;
3393}
3394
3378static int hugetlb_no_page(struct mm_struct *mm, struct vm_area_struct *vma, 3395static int hugetlb_no_page(struct mm_struct *mm, struct vm_area_struct *vma,
3379 struct address_space *mapping, pgoff_t idx, 3396 struct address_space *mapping, pgoff_t idx,
3380 unsigned long address, pte_t *ptep, unsigned int flags) 3397 unsigned long address, pte_t *ptep, unsigned int flags)
@@ -3422,21 +3439,13 @@ retry:
3422 set_page_huge_active(page); 3439 set_page_huge_active(page);
3423 3440
3424 if (vma->vm_flags & VM_MAYSHARE) { 3441 if (vma->vm_flags & VM_MAYSHARE) {
3425 int err; 3442 int err = huge_add_to_page_cache(page, mapping, idx);
3426 struct inode *inode = mapping->host;
3427
3428 err = add_to_page_cache(page, mapping, idx, GFP_KERNEL);
3429 if (err) { 3443 if (err) {
3430 put_page(page); 3444 put_page(page);
3431 if (err == -EEXIST) 3445 if (err == -EEXIST)
3432 goto retry; 3446 goto retry;
3433 goto out; 3447 goto out;
3434 } 3448 }
3435 ClearPagePrivate(page);
3436
3437 spin_lock(&inode->i_lock);
3438 inode->i_blocks += blocks_per_huge_page(h);
3439 spin_unlock(&inode->i_lock);
3440 } else { 3449 } else {
3441 lock_page(page); 3450 lock_page(page);
3442 if (unlikely(anon_vma_prepare(vma))) { 3451 if (unlikely(anon_vma_prepare(vma))) {