On Fri, Nov 8, 2024 at 8:38 AM Qi Zheng <zhengqi.arch@xxxxxxxxxxxxx> wrote: > On 2024/11/8 06:39, Jann Horn wrote: > > On Thu, Oct 31, 2024 at 9:14 AM Qi Zheng <zhengqi.arch@xxxxxxxxxxxxx> wrote: > > free_pte > > pte_free_tlb > > __pte_free_tlb > > ___pte_free_tlb > > paravirt_tlb_remove_table > > tlb_remove_table [!CONFIG_PARAVIRT, Xen PV, Hyper-V, KVM] > > [no-free-memory slowpath:] > > tlb_table_invalidate > > tlb_remove_table_one > > tlb_remove_table_sync_one [does IPI for GUP-fast] > > ^ > It seems that this step can be ommitted when > CONFIG_PT_RECLAIM is enabled, because GUP-fast will > disable IRQ, which can also serve as the RCU critical > section. Yeah, I think so too. > >> +#ifdef CONFIG_PT_RECLAIM > >> +static inline void __tlb_remove_table_one_rcu(struct rcu_head *head) > >> +{ > >> + struct page *page; > >> + > >> + page = container_of(head, struct page, rcu_head); > >> + free_page_and_swap_cache(page); > >> +} > > > > Why free_page_and_swap_cache()? Page tables shouldn't have swap cache, > > so I think something like put_page() would do the job. > > Ah, I just did the same thing as __tlb_remove_table(). But I also > have the same doubt as you, why does __tlb_remove_table() need to > call free_page_and_swap_cache() instead of put_page(). I think commit 9e52fc2b50de3a1c08b44f94c610fbe998c0031a probably just copy-pasted it from a more generic page freeing path...