Merge tag 'zonefs-5.10-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/dlemoal...
[linux-2.6-microblaze.git] / mm / huge_memory.c
index 65c289c..9474dbc 100644 (file)
@@ -2335,13 +2335,13 @@ static void unmap_page(struct page *page)
        VM_BUG_ON_PAGE(!unmap_success, page);
 }
 
-static void remap_page(struct page *page)
+static void remap_page(struct page *page, unsigned int nr)
 {
        int i;
        if (PageTransHuge(page)) {
                remove_migration_ptes(page, page, true);
        } else {
-               for (i = 0; i < HPAGE_PMD_NR; i++)
+               for (i = 0; i < nr; i++)
                        remove_migration_ptes(page + i, page + i, true);
        }
 }
@@ -2419,6 +2419,7 @@ static void __split_huge_page(struct page *page, struct list_head *list,
        struct lruvec *lruvec;
        struct address_space *swap_cache = NULL;
        unsigned long offset = 0;
+       unsigned int nr = thp_nr_pages(head);
        int i;
 
        lruvec = mem_cgroup_page_lruvec(head, pgdat);
@@ -2434,7 +2435,7 @@ static void __split_huge_page(struct page *page, struct list_head *list,
                xa_lock(&swap_cache->i_pages);
        }
 
-       for (i = HPAGE_PMD_NR - 1; i >= 1; i--) {
+       for (i = nr - 1; i >= 1; i--) {
                __split_huge_page_tail(head, i, lruvec, list);
                /* Some pages can be beyond i_size: drop them from page cache */
                if (head[i].index >= end) {
@@ -2454,7 +2455,7 @@ static void __split_huge_page(struct page *page, struct list_head *list,
 
        ClearPageCompound(head);
 
-       split_page_owner(head, HPAGE_PMD_ORDER);
+       split_page_owner(head, nr);
 
        /* See comment in __split_huge_page_tail() */
        if (PageAnon(head)) {
@@ -2473,9 +2474,15 @@ static void __split_huge_page(struct page *page, struct list_head *list,
 
        spin_unlock_irqrestore(&pgdat->lru_lock, flags);
 
-       remap_page(head);
+       remap_page(head, nr);
 
-       for (i = 0; i < HPAGE_PMD_NR; i++) {
+       if (PageSwapCache(head)) {
+               swp_entry_t entry = { .val = page_private(head) };
+
+               split_swap_cluster(entry);
+       }
+
+       for (i = 0; i < nr; i++) {
                struct page *subpage = head + i;
                if (subpage == page)
                        continue;
@@ -2494,7 +2501,7 @@ static void __split_huge_page(struct page *page, struct list_head *list,
 
 int total_mapcount(struct page *page)
 {
-       int i, compound, ret;
+       int i, compound, nr, ret;
 
        VM_BUG_ON_PAGE(PageTail(page), page);
 
@@ -2502,16 +2509,17 @@ int total_mapcount(struct page *page)
                return atomic_read(&page->_mapcount) + 1;
 
        compound = compound_mapcount(page);
+       nr = compound_nr(page);
        if (PageHuge(page))
                return compound;
        ret = compound;
-       for (i = 0; i < HPAGE_PMD_NR; i++)
+       for (i = 0; i < nr; i++)
                ret += atomic_read(&page[i]._mapcount) + 1;
        /* File pages has compound_mapcount included in _mapcount */
        if (!PageAnon(page))
-               return ret - compound * HPAGE_PMD_NR;
+               return ret - compound * nr;
        if (PageDoubleMap(page))
-               ret -= HPAGE_PMD_NR;
+               ret -= nr;
        return ret;
 }
 
@@ -2556,14 +2564,14 @@ int page_trans_huge_mapcount(struct page *page, int *total_mapcount)
        page = compound_head(page);
 
        _total_mapcount = ret = 0;
-       for (i = 0; i < HPAGE_PMD_NR; i++) {
+       for (i = 0; i < thp_nr_pages(page); i++) {
                mapcount = atomic_read(&page[i]._mapcount) + 1;
                ret = max(ret, mapcount);
                _total_mapcount += mapcount;
        }
        if (PageDoubleMap(page)) {
                ret -= 1;
-               _total_mapcount -= HPAGE_PMD_NR;
+               _total_mapcount -= thp_nr_pages(page);
        }
        mapcount = compound_mapcount(page);
        ret += mapcount;
@@ -2580,9 +2588,9 @@ bool can_split_huge_page(struct page *page, int *pextra_pins)
 
        /* Additional pins from page cache */
        if (PageAnon(page))
-               extra_pins = PageSwapCache(page) ? HPAGE_PMD_NR : 0;
+               extra_pins = PageSwapCache(page) ? thp_nr_pages(page) : 0;
        else
-               extra_pins = HPAGE_PMD_NR;
+               extra_pins = thp_nr_pages(page);
        if (pextra_pins)
                *pextra_pins = extra_pins;
        return total_mapcount(page) == page_count(page) - extra_pins - 1;
@@ -2709,12 +2717,7 @@ int split_huge_page_to_list(struct page *page, struct list_head *list)
                }
 
                __split_huge_page(page, list, end, flags);
-               if (PageSwapCache(head)) {
-                       swp_entry_t entry = { .val = page_private(head) };
-
-                       ret = split_swap_cluster(entry);
-               } else
-                       ret = 0;
+               ret = 0;
        } else {
                if (IS_ENABLED(CONFIG_DEBUG_VM) && mapcount) {
                        pr_alert("total_mapcount: %u, page_count(): %u\n",
@@ -2728,7 +2731,7 @@ int split_huge_page_to_list(struct page *page, struct list_head *list)
 fail:          if (mapping)
                        xa_unlock(&mapping->i_pages);
                spin_unlock_irqrestore(&pgdata->lru_lock, flags);
-               remap_page(head);
+               remap_page(head, thp_nr_pages(head));
                ret = -EBUSY;
        }