From: Kairui Song Pure cleanup, no functional change. After the priority queue replaced the allocator's device selection, swap_avail_head and swap_avail_lock are useless now. Remove them. __folio_throttle_swaprate() now iterates swap_active_head under swapon_rwsem instead, the SWP_WRITEOK filtering makes it equivalent to before. Signed-off-by: Kairui Song --- include/linux/swap.h | 1 - mm/swapfile.c | 30 ++++-------------------------- 2 files changed, 4 insertions(+), 27 deletions(-) diff --git a/include/linux/swap.h b/include/linux/swap.h index 6733a8979aa2..189c9898641b 100644 --- a/include/linux/swap.h +++ b/include/linux/swap.h @@ -293,7 +293,6 @@ struct swap_info_struct { struct work_struct discard_work; /* discard worker */ struct work_struct reclaim_work; /* reclaim worker */ struct list_head discard_clusters; /* discard clusters list */ - struct plist_node avail_list; /* entry in swap_avail_head */ }; static inline swp_entry_t page_swap_entry(struct page *page) diff --git a/mm/swapfile.c b/mm/swapfile.c index f6dd85968928..01240c4c9db3 100644 --- a/mm/swapfile.c +++ b/mm/swapfile.c @@ -96,21 +96,6 @@ static const char Bad_offset[] = "Bad swap offset entry "; */ static PLIST_HEAD(swap_active_head); -/* - * all available (active, not full) swap_info_structs - * protected with swap_avail_lock, ordered by priority. - * This is used by folio_alloc_swap() instead of swap_active_head - * because swap_active_head includes all swap_info_structs, - * but folio_alloc_swap() doesn't need to look at full ones. - * This uses its own lock instead of swapon_rwsem because when a - * swap_info_struct changes between not-full/full, it needs to - * add/remove itself to/from this list, but the swap_info_struct->lock - * is held and the locking order requires swapon_rwsem to be taken - * before any swap_info_struct->lock. - */ -static PLIST_HEAD(swap_avail_head); -static DEFINE_SPINLOCK(swap_avail_lock); - static inline struct swap_info_struct *__swap_iter(int *i, unsigned long flag) { lockdep_assert_held(&swapon_rwsem); @@ -1547,7 +1532,6 @@ static void del_from_avail_list(struct swap_info_struct *si, bool swapoff) { unsigned long pages; - spin_lock(&swap_avail_lock); spin_lock(&swap_queue_update_lock); /* @@ -1567,10 +1551,8 @@ static void del_from_avail_list(struct swap_info_struct *si, bool swapoff) } swap_queue_mask(si); - plist_del(&si->avail_list, &swap_avail_head); skip: spin_unlock(&swap_queue_update_lock); - spin_unlock(&swap_avail_lock); } /* SWAP_USAGE_OFFLIST_BIT can only be cleared by this helper. */ @@ -1579,7 +1561,6 @@ static void add_to_avail_list(struct swap_info_struct *si) long val; unsigned long pages; - spin_lock(&swap_avail_lock); spin_lock(&swap_queue_update_lock); /* @@ -1610,7 +1591,6 @@ static void add_to_avail_list(struct swap_info_struct *si) } swap_queue_unmask(si); - plist_add(&si->avail_list, &swap_avail_head); skip: spin_unlock(&swap_queue_update_lock); } @@ -3622,7 +3602,6 @@ static struct swap_info_struct *alloc_swap_info(void) } p->swap_extent_root = RB_ROOT; plist_node_init(&p->list, 0); - plist_node_init(&p->avail_list, 0); p->flags = SWP_USED; percpu_up_write(&swapon_rwsem); if (defer) { @@ -4030,7 +4009,6 @@ SYSCALL_DEFINE2(swapon, const char __user *, specialfile, int, swap_flags) */ si->prio = prio; si->list.prio = -si->prio; - si->avail_list.prio = -si->prio; si->swap_file = swap_file; /* Sets SWP_WRITEOK, resurrect the percpu ref, expose the swap device */ @@ -4163,14 +4141,14 @@ void __folio_throttle_swaprate(struct folio *folio, gfp_t gfp) if (current->throttle_disk) return; - spin_lock(&swap_avail_lock); - plist_for_each_entry(si, &swap_avail_head, avail_list) { - if (si->bdev) { + percpu_down_read(&swapon_rwsem); + plist_for_each_entry(si, &swap_active_head, list) { + if ((si->flags & SWP_WRITEOK) && si->bdev) { blkcg_schedule_throttle(si->bdev->bd_disk, true); break; } } - spin_unlock(&swap_avail_lock); + percpu_up_read(&swapon_rwsem); } #endif -- 2.55.0