Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

huge_memory: convert split_huge_page_to_list() to use a folio

Saves many calls to compound_head().

Link: https://lkml.kernel.org/r/20220902194653.1739778-53-willy@infradead.org
Signed-off-by: Matthew Wilcox (Oracle) <willy@infradead.org>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>

authored by

Matthew Wilcox (Oracle) and committed by
Andrew Morton
3e9a13da c33db292

+24 -25
+24 -25
mm/huge_memory.c
··· 2622 2622 int split_huge_page_to_list(struct page *page, struct list_head *list) 2623 2623 { 2624 2624 struct folio *folio = page_folio(page); 2625 - struct page *head = &folio->page; 2626 - struct deferred_split *ds_queue = get_deferred_split_queue(head); 2627 - XA_STATE(xas, &head->mapping->i_pages, head->index); 2625 + struct deferred_split *ds_queue = get_deferred_split_queue(&folio->page); 2626 + XA_STATE(xas, &folio->mapping->i_pages, folio->index); 2628 2627 struct anon_vma *anon_vma = NULL; 2629 2628 struct address_space *mapping = NULL; 2630 2629 int extra_pins, ret; 2631 2630 pgoff_t end; 2632 2631 bool is_hzp; 2633 2632 2634 - VM_BUG_ON_PAGE(!PageLocked(head), head); 2635 - VM_BUG_ON_PAGE(!PageCompound(head), head); 2633 + VM_BUG_ON_FOLIO(!folio_test_locked(folio), folio); 2634 + VM_BUG_ON_FOLIO(!folio_test_large(folio), folio); 2636 2635 2637 - is_hzp = is_huge_zero_page(head); 2638 - VM_WARN_ON_ONCE_PAGE(is_hzp, head); 2636 + is_hzp = is_huge_zero_page(&folio->page); 2637 + VM_WARN_ON_ONCE_FOLIO(is_hzp, folio); 2639 2638 if (is_hzp) 2640 2639 return -EBUSY; 2641 2640 2642 - if (PageWriteback(head)) 2641 + if (folio_test_writeback(folio)) 2643 2642 return -EBUSY; 2644 2643 2645 - if (PageAnon(head)) { 2644 + if (folio_test_anon(folio)) { 2646 2645 /* 2647 2646 * The caller does not necessarily hold an mmap_lock that would 2648 2647 * prevent the anon_vma disappearing so we first we take a ··· 2650 2651 * is taken to serialise against parallel split or collapse 2651 2652 * operations. 2652 2653 */ 2653 - anon_vma = page_get_anon_vma(head); 2654 + anon_vma = page_get_anon_vma(&folio->page); 2654 2655 if (!anon_vma) { 2655 2656 ret = -EBUSY; 2656 2657 goto out; ··· 2661 2662 } else { 2662 2663 gfp_t gfp; 2663 2664 2664 - mapping = head->mapping; 2665 + mapping = folio->mapping; 2665 2666 2666 2667 /* Truncated ? */ 2667 2668 if (!mapping) { ··· 2678 2679 goto out; 2679 2680 } 2680 2681 2681 - xas_split_alloc(&xas, head, compound_order(head), gfp); 2682 + xas_split_alloc(&xas, folio, folio_order(folio), gfp); 2682 2683 if (xas_error(&xas)) { 2683 2684 ret = xas_error(&xas); 2684 2685 goto out; ··· 2692 2693 * but on 32-bit, i_size_read() takes an irq-unsafe seqlock, 2693 2694 * which cannot be nested inside the page tree lock. So note 2694 2695 * end now: i_size itself may be changed at any moment, but 2695 - * head page lock is good enough to serialize the trimming. 2696 + * folio lock is good enough to serialize the trimming. 2696 2697 */ 2697 2698 end = DIV_ROUND_UP(i_size_read(mapping->host), PAGE_SIZE); 2698 2699 if (shmem_mapping(mapping)) ··· 2708 2709 goto out_unlock; 2709 2710 } 2710 2711 2711 - unmap_page(head); 2712 + unmap_page(&folio->page); 2712 2713 2713 2714 /* block interrupt reentry in xa_lock and spinlock */ 2714 2715 local_irq_disable(); 2715 2716 if (mapping) { 2716 2717 /* 2717 - * Check if the head page is present in page cache. 2718 - * We assume all tail are present too, if head is there. 2718 + * Check if the folio is present in page cache. 2719 + * We assume all tail are present too, if folio is there. 2719 2720 */ 2720 2721 xas_lock(&xas); 2721 2722 xas_reset(&xas); 2722 - if (xas_load(&xas) != head) 2723 + if (xas_load(&xas) != folio) 2723 2724 goto fail; 2724 2725 } 2725 2726 2726 2727 /* Prevent deferred_split_scan() touching ->_refcount */ 2727 2728 spin_lock(&ds_queue->split_queue_lock); 2728 - if (page_ref_freeze(head, 1 + extra_pins)) { 2729 - if (!list_empty(page_deferred_list(head))) { 2729 + if (folio_ref_freeze(folio, 1 + extra_pins)) { 2730 + if (!list_empty(page_deferred_list(&folio->page))) { 2730 2731 ds_queue->split_queue_len--; 2731 - list_del(page_deferred_list(head)); 2732 + list_del(page_deferred_list(&folio->page)); 2732 2733 } 2733 2734 spin_unlock(&ds_queue->split_queue_lock); 2734 2735 if (mapping) { 2735 - int nr = thp_nr_pages(head); 2736 + int nr = folio_nr_pages(folio); 2736 2737 2737 - xas_split(&xas, head, thp_order(head)); 2738 - if (PageSwapBacked(head)) { 2739 - __mod_lruvec_page_state(head, NR_SHMEM_THPS, 2738 + xas_split(&xas, folio, folio_order(folio)); 2739 + if (folio_test_swapbacked(folio)) { 2740 + __lruvec_stat_mod_folio(folio, NR_SHMEM_THPS, 2740 2741 -nr); 2741 2742 } else { 2742 - __mod_lruvec_page_state(head, NR_FILE_THPS, 2743 + __lruvec_stat_mod_folio(folio, NR_FILE_THPS, 2743 2744 -nr); 2744 2745 filemap_nr_thps_dec(mapping); 2745 2746 }