* [PATCH v3 0/2] mm/swapfile.c and swap.h cleanup @ 2025-08-12 7:10 Chris Li 2025-08-12 7:10 ` [PATCH v3 1/2] mm/swapfile.c: introduce function alloc_swap_scan_list() Chris Li 2025-08-12 7:10 ` [PATCH v3 2/2] mm: swap.h: Remove deleted field from comments Chris Li 0 siblings, 2 replies; 9+ messages in thread From: Chris Li @ 2025-08-12 7:10 UTC (permalink / raw) To: Andrew Morton, Kemeng Shi, Kairui Song, Nhat Pham, Baoquan He, Barry Song, Huang, Ying Cc: linux-mm, linux-kernel, Chris Li This patch series, which builds on Kairui's swap improve cluster scan series. https://lore.kernel.org/linux-mm/20250806161748.76651-1-ryncsn@gmail.com/ It introduces a new function, alloc_swap_scan_list(), for swapfile.c. It also cleans up swap.h by removing comments that reference fields that have been deleted. There are no functional changes in this two-patch series. Signed-off-by: Chris Li <chrisl@kernel.org> --- Changes in v3: - Fix a few scan_all argument to match having while loop or not. - Update comment message. - Add a ptach to clean up the comments in swap.h - Link to v2: https://lore.kernel.org/r/20250808-swap-scan-list-v2-1-d50e4758ecee@kernel.org Changes in v2: - Adjust change base on Andrew's feedback on int type and break out of loop. - Link to v1: https://lore.kernel.org/r/20250806-swap-scan-list-v1-1-a5fe2d9340a2@kernel.org --- Chris Li (2): mm/swapfile.c: introduce function alloc_swap_scan_list() mm: swap.h: Remove deleted field from comments include/linux/swap.h | 7 ++--- mm/swapfile.c | 86 ++++++++++++++++++++++++++++------------------------ 2 files changed, 49 insertions(+), 44 deletions(-) --- base-commit: f89484324d5876ee10765fa61da0332899fa1a6a change-id: 20250806-swap-scan-list-2b89e3424b0a Best regards, -- Chris Li <chrisl@kernel.org> ^ permalink raw reply [flat|nested] 9+ messages in thread
* [PATCH v3 1/2] mm/swapfile.c: introduce function alloc_swap_scan_list() 2025-08-12 7:10 [PATCH v3 0/2] mm/swapfile.c and swap.h cleanup Chris Li @ 2025-08-12 7:10 ` Chris Li 2025-08-12 16:56 ` Kairui Song 2025-08-13 14:57 ` Nhat Pham 2025-08-12 7:10 ` [PATCH v3 2/2] mm: swap.h: Remove deleted field from comments Chris Li 1 sibling, 2 replies; 9+ messages in thread From: Chris Li @ 2025-08-12 7:10 UTC (permalink / raw) To: Andrew Morton, Kemeng Shi, Kairui Song, Nhat Pham, Baoquan He, Barry Song, Huang, Ying Cc: linux-mm, linux-kernel, Chris Li alloc_swap_scan_list() will scan the whole list or the first cluster. This reduces the repeat patterns of isolating a cluster then scanning that cluster. As a result, cluster_alloc_swap_entry() is shorter and shallower. No functional change. Signed-off-by: Chris Li <chrisl@kernel.org> --- mm/swapfile.c | 86 ++++++++++++++++++++++++++++++++--------------------------- 1 file changed, 47 insertions(+), 39 deletions(-) diff --git a/mm/swapfile.c b/mm/swapfile.c index 4a0cf4fb348d..a7ffabbe65ef 100644 --- a/mm/swapfile.c +++ b/mm/swapfile.c @@ -820,6 +820,29 @@ static unsigned int alloc_swap_scan_cluster(struct swap_info_struct *si, return found; } +static unsigned int alloc_swap_scan_list(struct swap_info_struct *si, + struct list_head *list, + unsigned int order, + unsigned char usage, + bool scan_all) +{ + unsigned int found = SWAP_ENTRY_INVALID; + + do { + struct swap_cluster_info *ci = isolate_lock_cluster(si, list); + unsigned long offset; + + if (!ci) + break; + offset = cluster_offset(si, ci); + found = alloc_swap_scan_cluster(si, ci, offset, order, usage); + if (found) + break; + } while (scan_all); + + return found; +} + static void swap_reclaim_full_clusters(struct swap_info_struct *si, bool force) { long to_scan = 1; @@ -913,32 +936,24 @@ static unsigned long cluster_alloc_swap_entry(struct swap_info_struct *si, int o * to spread out the writes. */ if (si->flags & SWP_PAGE_DISCARD) { - ci = isolate_lock_cluster(si, &si->free_clusters); - if (ci) { - found = alloc_swap_scan_cluster(si, ci, cluster_offset(si, ci), - order, usage); - if (found) - goto done; - } + found = alloc_swap_scan_list(si, &si->free_clusters, order, usage, + false); + if (found) + goto done; } if (order < PMD_ORDER) { - while ((ci = isolate_lock_cluster(si, &si->nonfull_clusters[order]))) { - found = alloc_swap_scan_cluster(si, ci, cluster_offset(si, ci), - order, usage); - if (found) - goto done; - } + found = alloc_swap_scan_list(si, &si->nonfull_clusters[order], + order, usage, true); + if (found) + goto done; } if (!(si->flags & SWP_PAGE_DISCARD)) { - ci = isolate_lock_cluster(si, &si->free_clusters); - if (ci) { - found = alloc_swap_scan_cluster(si, ci, cluster_offset(si, ci), - order, usage); - if (found) - goto done; - } + found = alloc_swap_scan_list(si, &si->free_clusters, order, usage, + false); + if (found) + goto done; } /* Try reclaim full clusters if free and nonfull lists are drained */ @@ -952,13 +967,10 @@ static unsigned long cluster_alloc_swap_entry(struct swap_info_struct *si, int o * failure is not critical. Scanning one cluster still * keeps the list rotated and reclaimed (for HAS_CACHE). */ - ci = isolate_lock_cluster(si, &si->frag_clusters[order]); - if (ci) { - found = alloc_swap_scan_cluster(si, ci, cluster_offset(si, ci), - order, usage); - if (found) - goto done; - } + found = alloc_swap_scan_list(si, &si->frag_clusters[order], order, + usage, false); + if (found) + goto done; } /* @@ -977,19 +989,15 @@ static unsigned long cluster_alloc_swap_entry(struct swap_info_struct *si, int o * Clusters here have at least one usable slots and can't fail order 0 * allocation, but reclaim may drop si->lock and race with another user. */ - while ((ci = isolate_lock_cluster(si, &si->frag_clusters[o]))) { - found = alloc_swap_scan_cluster(si, ci, cluster_offset(si, ci), - 0, usage); - if (found) - goto done; - } + found = alloc_swap_scan_list(si, &si->frag_clusters[o], + 0, usage, true); + if (found) + goto done; - while ((ci = isolate_lock_cluster(si, &si->nonfull_clusters[o]))) { - found = alloc_swap_scan_cluster(si, ci, cluster_offset(si, ci), - 0, usage); - if (found) - goto done; - } + found = alloc_swap_scan_list(si, &si->nonfull_clusters[o], + 0, usage, true); + if (found) + goto done; } done: if (!(si->flags & SWP_SOLIDSTATE)) -- 2.43.0 ^ permalink raw reply related [flat|nested] 9+ messages in thread
* Re: [PATCH v3 1/2] mm/swapfile.c: introduce function alloc_swap_scan_list() 2025-08-12 7:10 ` [PATCH v3 1/2] mm/swapfile.c: introduce function alloc_swap_scan_list() Chris Li @ 2025-08-12 16:56 ` Kairui Song 2025-08-13 6:13 ` Chris Li 2025-08-13 14:57 ` Nhat Pham 1 sibling, 1 reply; 9+ messages in thread From: Kairui Song @ 2025-08-12 16:56 UTC (permalink / raw) To: Chris Li Cc: Andrew Morton, Kemeng Shi, Nhat Pham, Baoquan He, Barry Song, Huang, Ying, linux-mm, linux-kernel On Tue, Aug 12, 2025 at 5:13 PM Chris Li <chrisl@kernel.org> wrote: > > alloc_swap_scan_list() will scan the whole list or the first cluster. > > This reduces the repeat patterns of isolating a cluster then scanning that > cluster. As a result, cluster_alloc_swap_entry() is shorter and shallower. > > No functional change. > > Signed-off-by: Chris Li <chrisl@kernel.org> > --- > mm/swapfile.c | 86 ++++++++++++++++++++++++++++++++--------------------------- > 1 file changed, 47 insertions(+), 39 deletions(-) > > diff --git a/mm/swapfile.c b/mm/swapfile.c > index 4a0cf4fb348d..a7ffabbe65ef 100644 > --- a/mm/swapfile.c > +++ b/mm/swapfile.c > @@ -820,6 +820,29 @@ static unsigned int alloc_swap_scan_cluster(struct swap_info_struct *si, > return found; > } > > +static unsigned int alloc_swap_scan_list(struct swap_info_struct *si, > + struct list_head *list, > + unsigned int order, > + unsigned char usage, > + bool scan_all) > +{ > + unsigned int found = SWAP_ENTRY_INVALID; > + > + do { > + struct swap_cluster_info *ci = isolate_lock_cluster(si, list); > + unsigned long offset; > + > + if (!ci) > + break; > + offset = cluster_offset(si, ci); > + found = alloc_swap_scan_cluster(si, ci, offset, order, usage); > + if (found) > + break; > + } while (scan_all); > + > + return found; > +} > + > static void swap_reclaim_full_clusters(struct swap_info_struct *si, bool force) > { > long to_scan = 1; > @@ -913,32 +936,24 @@ static unsigned long cluster_alloc_swap_entry(struct swap_info_struct *si, int o > * to spread out the writes. > */ > if (si->flags & SWP_PAGE_DISCARD) { > - ci = isolate_lock_cluster(si, &si->free_clusters); > - if (ci) { > - found = alloc_swap_scan_cluster(si, ci, cluster_offset(si, ci), > - order, usage); > - if (found) > - goto done; > - } > + found = alloc_swap_scan_list(si, &si->free_clusters, order, usage, > + false); > + if (found) > + goto done; > } > > if (order < PMD_ORDER) { > - while ((ci = isolate_lock_cluster(si, &si->nonfull_clusters[order]))) { > - found = alloc_swap_scan_cluster(si, ci, cluster_offset(si, ci), > - order, usage); > - if (found) > - goto done; > - } > + found = alloc_swap_scan_list(si, &si->nonfull_clusters[order], > + order, usage, true); > + if (found) > + goto done; > } > > if (!(si->flags & SWP_PAGE_DISCARD)) { > - ci = isolate_lock_cluster(si, &si->free_clusters); > - if (ci) { > - found = alloc_swap_scan_cluster(si, ci, cluster_offset(si, ci), > - order, usage); > - if (found) > - goto done; > - } > + found = alloc_swap_scan_list(si, &si->free_clusters, order, usage, > + false); > + if (found) > + goto done; > } > > /* Try reclaim full clusters if free and nonfull lists are drained */ > @@ -952,13 +967,10 @@ static unsigned long cluster_alloc_swap_entry(struct swap_info_struct *si, int o > * failure is not critical. Scanning one cluster still > * keeps the list rotated and reclaimed (for HAS_CACHE). > */ > - ci = isolate_lock_cluster(si, &si->frag_clusters[order]); > - if (ci) { > - found = alloc_swap_scan_cluster(si, ci, cluster_offset(si, ci), > - order, usage); > - if (found) > - goto done; > - } > + found = alloc_swap_scan_list(si, &si->frag_clusters[order], order, > + usage, false); > + if (found) > + goto done; > } > > /* > @@ -977,19 +989,15 @@ static unsigned long cluster_alloc_swap_entry(struct swap_info_struct *si, int o > * Clusters here have at least one usable slots and can't fail order 0 > * allocation, but reclaim may drop si->lock and race with another user. > */ > - while ((ci = isolate_lock_cluster(si, &si->frag_clusters[o]))) { > - found = alloc_swap_scan_cluster(si, ci, cluster_offset(si, ci), > - 0, usage); > - if (found) > - goto done; > - } > + found = alloc_swap_scan_list(si, &si->frag_clusters[o], > + 0, usage, true); > + if (found) > + goto done; > > - while ((ci = isolate_lock_cluster(si, &si->nonfull_clusters[o]))) { > - found = alloc_swap_scan_cluster(si, ci, cluster_offset(si, ci), > - 0, usage); > - if (found) > - goto done; > - } > + found = alloc_swap_scan_list(si, &si->nonfull_clusters[o], > + 0, usage, true); > + if (found) > + goto done; > } > done: > if (!(si->flags & SWP_SOLIDSTATE)) > > -- > 2.43.0 > I've been testing on top of a locally updated version of V2 for about two days, and it's identical to this one. This looks great, thanks! Reviewed-by: Kairui Song <kasong@tencent.com> ^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH v3 1/2] mm/swapfile.c: introduce function alloc_swap_scan_list() 2025-08-12 16:56 ` Kairui Song @ 2025-08-13 6:13 ` Chris Li 0 siblings, 0 replies; 9+ messages in thread From: Chris Li @ 2025-08-13 6:13 UTC (permalink / raw) To: Kairui Song Cc: Andrew Morton, Kemeng Shi, Nhat Pham, Baoquan He, Barry Song, Huang, Ying, linux-mm, linux-kernel On Tue, Aug 12, 2025 at 9:57 AM Kairui Song <ryncsn@gmail.com> wrote: > > I've been testing on top of a locally updated version of V2 for about > two days, and it's identical to this one. This looks great, thanks! Thanks for the review. I have been running the swap stress tests on kernel compile as well. No issue so far. Chris ^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH v3 1/2] mm/swapfile.c: introduce function alloc_swap_scan_list() 2025-08-12 7:10 ` [PATCH v3 1/2] mm/swapfile.c: introduce function alloc_swap_scan_list() Chris Li 2025-08-12 16:56 ` Kairui Song @ 2025-08-13 14:57 ` Nhat Pham 1 sibling, 0 replies; 9+ messages in thread From: Nhat Pham @ 2025-08-13 14:57 UTC (permalink / raw) To: Chris Li Cc: Andrew Morton, Kemeng Shi, Kairui Song, Baoquan He, Barry Song, Huang, Ying, linux-mm, linux-kernel On Tue, Aug 12, 2025 at 12:10 AM Chris Li <chrisl@kernel.org> wrote: > > alloc_swap_scan_list() will scan the whole list or the first cluster. > > This reduces the repeat patterns of isolating a cluster then scanning that > cluster. As a result, cluster_alloc_swap_entry() is shorter and shallower. > > No functional change. > > Signed-off-by: Chris Li <chrisl@kernel.org> Code seems more readable now, IMO. Thanks, Chris! Acked-by: Nhat Pham <nphamcs@gmail.com> ^ permalink raw reply [flat|nested] 9+ messages in thread
* [PATCH v3 2/2] mm: swap.h: Remove deleted field from comments 2025-08-12 7:10 [PATCH v3 0/2] mm/swapfile.c and swap.h cleanup Chris Li 2025-08-12 7:10 ` [PATCH v3 1/2] mm/swapfile.c: introduce function alloc_swap_scan_list() Chris Li @ 2025-08-12 7:10 ` Chris Li 2025-08-12 17:04 ` Kairui Song ` (2 more replies) 1 sibling, 3 replies; 9+ messages in thread From: Chris Li @ 2025-08-12 7:10 UTC (permalink / raw) To: Andrew Morton, Kemeng Shi, Kairui Song, Nhat Pham, Baoquan He, Barry Song, Huang, Ying Cc: linux-mm, linux-kernel, Chris Li The comment for struct swap_info_struct.lock incorrectly mentions fields that have already been deleted from the structure. Updates the comments to accurately reflect the current struct swap_info_struct. There is no functional change. Signed-off-by: Chris Li <chrisl@kernel.org> --- include/linux/swap.h | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/include/linux/swap.h b/include/linux/swap.h index a060d102e0d1..c2da85cb7fe7 100644 --- a/include/linux/swap.h +++ b/include/linux/swap.h @@ -320,11 +320,8 @@ struct swap_info_struct { struct completion comp; /* seldom referenced */ spinlock_t lock; /* * protect map scan related fields like - * swap_map, lowest_bit, highest_bit, - * inuse_pages, cluster_next, - * cluster_nr, lowest_alloc, - * highest_alloc, free/discard cluster - * list. other fields are only changed + * swap_map, inuse_pages and all cluster + * lists. other fields are only changed * at swapon/swapoff, so are protected * by swap_lock. changing flags need * hold this lock and swap_lock. If -- 2.43.0 ^ permalink raw reply related [flat|nested] 9+ messages in thread
* Re: [PATCH v3 2/2] mm: swap.h: Remove deleted field from comments 2025-08-12 7:10 ` [PATCH v3 2/2] mm: swap.h: Remove deleted field from comments Chris Li @ 2025-08-12 17:04 ` Kairui Song 2025-08-13 11:05 ` Barry Song 2025-08-13 14:58 ` Nhat Pham 2 siblings, 0 replies; 9+ messages in thread From: Kairui Song @ 2025-08-12 17:04 UTC (permalink / raw) To: Chris Li Cc: Andrew Morton, Kemeng Shi, Nhat Pham, Baoquan He, Barry Song, Huang, Ying, linux-mm, linux-kernel On Tue, Aug 12, 2025 at 3:26 PM Chris Li <chrisl@kernel.org> wrote: > > The comment for struct swap_info_struct.lock incorrectly mentions fields > that have already been deleted from the structure. > > Updates the comments to accurately reflect the current struct > swap_info_struct. > > There is no functional change. > > Signed-off-by: Chris Li <chrisl@kernel.org> > --- > include/linux/swap.h | 7 ++----- > 1 file changed, 2 insertions(+), 5 deletions(-) > > diff --git a/include/linux/swap.h b/include/linux/swap.h > index a060d102e0d1..c2da85cb7fe7 100644 > --- a/include/linux/swap.h > +++ b/include/linux/swap.h > @@ -320,11 +320,8 @@ struct swap_info_struct { > struct completion comp; /* seldom referenced */ > spinlock_t lock; /* > * protect map scan related fields like > - * swap_map, lowest_bit, highest_bit, > - * inuse_pages, cluster_next, > - * cluster_nr, lowest_alloc, > - * highest_alloc, free/discard cluster > - * list. other fields are only changed > + * swap_map, inuse_pages and all cluster > + * lists. other fields are only changed > * at swapon/swapoff, so are protected > * by swap_lock. changing flags need > * hold this lock and swap_lock. If > > -- > 2.43.0 > Thanks. Reviewed-by: Kairui Song <kasong@tencent.com> ^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH v3 2/2] mm: swap.h: Remove deleted field from comments 2025-08-12 7:10 ` [PATCH v3 2/2] mm: swap.h: Remove deleted field from comments Chris Li 2025-08-12 17:04 ` Kairui Song @ 2025-08-13 11:05 ` Barry Song 2025-08-13 14:58 ` Nhat Pham 2 siblings, 0 replies; 9+ messages in thread From: Barry Song @ 2025-08-13 11:05 UTC (permalink / raw) To: Chris Li Cc: Andrew Morton, Kemeng Shi, Kairui Song, Nhat Pham, Baoquan He, Huang, Ying, linux-mm, linux-kernel On Tue, Aug 12, 2025 at 3:11 PM Chris Li <chrisl@kernel.org> wrote: > > The comment for struct swap_info_struct.lock incorrectly mentions fields > that have already been deleted from the structure. > > Updates the comments to accurately reflect the current struct > swap_info_struct. > > There is no functional change. > > Signed-off-by: Chris Li <chrisl@kernel.org> Reviewed-by: Barry Song <baohua@kernel.org> Thanks Barry ^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH v3 2/2] mm: swap.h: Remove deleted field from comments 2025-08-12 7:10 ` [PATCH v3 2/2] mm: swap.h: Remove deleted field from comments Chris Li 2025-08-12 17:04 ` Kairui Song 2025-08-13 11:05 ` Barry Song @ 2025-08-13 14:58 ` Nhat Pham 2 siblings, 0 replies; 9+ messages in thread From: Nhat Pham @ 2025-08-13 14:58 UTC (permalink / raw) To: Chris Li Cc: Andrew Morton, Kemeng Shi, Kairui Song, Baoquan He, Barry Song, Huang, Ying, linux-mm, linux-kernel On Tue, Aug 12, 2025 at 12:11 AM Chris Li <chrisl@kernel.org> wrote: > > The comment for struct swap_info_struct.lock incorrectly mentions fields > that have already been deleted from the structure. > > Updates the comments to accurately reflect the current struct > swap_info_struct. > > There is no functional change. > > Signed-off-by: Chris Li <chrisl@kernel.org> Acked-by: Nhat Pham <nphamcs@gmail.com> ^ permalink raw reply [flat|nested] 9+ messages in thread
end of thread, other threads:[~2025-08-13 14:58 UTC | newest] Thread overview: 9+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2025-08-12 7:10 [PATCH v3 0/2] mm/swapfile.c and swap.h cleanup Chris Li 2025-08-12 7:10 ` [PATCH v3 1/2] mm/swapfile.c: introduce function alloc_swap_scan_list() Chris Li 2025-08-12 16:56 ` Kairui Song 2025-08-13 6:13 ` Chris Li 2025-08-13 14:57 ` Nhat Pham 2025-08-12 7:10 ` [PATCH v3 2/2] mm: swap.h: Remove deleted field from comments Chris Li 2025-08-12 17:04 ` Kairui Song 2025-08-13 11:05 ` Barry Song 2025-08-13 14:58 ` Nhat Pham
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for NNTP newsgroup(s).