On Sun, Jan 12, 2025 at 4:55 PM Rik van Riel <riel@xxxxxxxxxxx> wrote: > Use the INVLPGB_FINAL_ONLY flag when invalidating mappings with INVPLGB. > This way only leaf mappings get removed from the TLB, leaving intermediate > translations cached. > > On the (rare) occasions where we free page tables we do a full flush, > ensuring intermediate translations get flushed from the TLB. > > Signed-off-by: Rik van Riel <riel@xxxxxxxxxxx> > --- > arch/x86/include/asm/invlpgb.h | 10 ++++++++-- > arch/x86/mm/tlb.c | 8 ++++---- > 2 files changed, 12 insertions(+), 6 deletions(-) > > diff --git a/arch/x86/include/asm/invlpgb.h b/arch/x86/include/asm/invlpgb.h > index d62e3733a1ab..4fa48d063b76 100644 > --- a/arch/x86/include/asm/invlpgb.h > +++ b/arch/x86/include/asm/invlpgb.h > @@ -61,9 +61,15 @@ static inline void invlpgb_flush_user(unsigned long pcid, > > static inline void invlpgb_flush_user_nr_nosync(unsigned long pcid, > unsigned long addr, > - int nr, bool pmd_stride) > + int nr, bool pmd_stride, > + bool freed_tables) > { > - __invlpgb(0, pcid, addr, nr - 1, pmd_stride, INVLPGB_PCID | INVLPGB_VA); > + unsigned long flags = INVLPGB_PCID | INVLPGB_VA; > + > + if (!freed_tables) > + flags |= INVLPGB_FINAL_ONLY; > + > + __invlpgb(0, pcid, addr, nr - 1, pmd_stride, flags); > } Thanks, this looks much nicer to me.