diff mbox series

[RFC,2/2] mm: mmu_notifier fix for tlb_end_vma

Message ID 20180823084709.19717-3-npiggin@gmail.com (mailing list archive)
State New, archived
Headers show
Series minor mmu_gather patches | expand

Commit Message

Nicholas Piggin Aug. 23, 2018, 8:47 a.m. UTC
The generic tlb_end_vma does not call invalidate_range mmu notifier,
and it resets resets the mmu_gather range, which means the notifier
won't be called on part of the range in case of an unmap that spans
multiple vmas.

ARM64 seems to be the only arch I could see that has notifiers and
uses the generic tlb_end_vma. I have not actually tested it.

Signed-off-by: Nicholas Piggin <npiggin@gmail.com>
---
 include/asm-generic/tlb.h | 17 +++++++++++++----
 mm/memory.c               | 10 ----------
 2 files changed, 13 insertions(+), 14 deletions(-)

Comments

Catalin Marinas Aug. 23, 2018, 12:46 p.m. UTC | #1
On Thu, Aug 23, 2018 at 06:47:09PM +1000, Nicholas Piggin wrote:
> The generic tlb_end_vma does not call invalidate_range mmu notifier,
> and it resets resets the mmu_gather range, which means the notifier
> won't be called on part of the range in case of an unmap that spans
> multiple vmas.
> 
> ARM64 seems to be the only arch I could see that has notifiers and
> uses the generic tlb_end_vma. I have not actually tested it.

We only care about notifiers for KVM but I think it only makes use of
mmu_notifier_invalidate_range_(start|end) which are not affected by the
range reset in mmu_gather.

Your patch looks ok from an arm64 perspective (it would be good if Will
has a look as well since he was the last to touch this part for arm64).
Will Deacon Aug. 23, 2018, 1:41 p.m. UTC | #2
On Thu, Aug 23, 2018 at 06:47:09PM +1000, Nicholas Piggin wrote:
> The generic tlb_end_vma does not call invalidate_range mmu notifier,
> and it resets resets the mmu_gather range, which means the notifier
> won't be called on part of the range in case of an unmap that spans
> multiple vmas.
> 
> ARM64 seems to be the only arch I could see that has notifiers and
> uses the generic tlb_end_vma. I have not actually tested it.
> 
> Signed-off-by: Nicholas Piggin <npiggin@gmail.com>
> ---
>  include/asm-generic/tlb.h | 17 +++++++++++++----
>  mm/memory.c               | 10 ----------
>  2 files changed, 13 insertions(+), 14 deletions(-)

I think we only use the notifiers in the KVM code, which appears to leave
the ->invalidate_range() callback empty, so that at least explains why we
haven't run into problems here.

But the change looks correct to me, so:

Acked-by: Will Deacon <will.deacon@arm.com>

Thanks,

Will
Guenter Roeck Aug. 24, 2018, 1:07 p.m. UTC | #3
On Thu, Aug 23, 2018 at 06:47:09PM +1000, Nicholas Piggin wrote:
> The generic tlb_end_vma does not call invalidate_range mmu notifier,
> and it resets resets the mmu_gather range, which means the notifier
> won't be called on part of the range in case of an unmap that spans
> multiple vmas.
> 
> ARM64 seems to be the only arch I could see that has notifiers and
> uses the generic tlb_end_vma. I have not actually tested it.
> 
> Signed-off-by: Nicholas Piggin <npiggin@gmail.com>
> Acked-by: Will Deacon <will.deacon@arm.com>

This patch breaks riscv builds in mainline.

Building riscv:defconfig ... failed
--------------
Error log:
In file included from riscv/include/asm/tlb.h:17:0,
                 from arch/riscv/include/asm/pgalloc.h:19,
                 from riscv/mm/fault.c:30:
include/asm-generic/tlb.h: In function 'tlb_flush_mmu_tlbonly':
include/asm-generic/tlb.h:147:2: error: implicit declaration of function 'tlb_flush'

In file included from arch/riscv/include/asm/pgalloc.h:19:0,
		from arch/riscv/mm/fault.c:30:
arch/riscv/include/asm/tlb.h: At top level:
arch/riscv/include/asm/tlb.h:19:20: warning: conflicting types for 'tlb_flush'

Guenter
Will Deacon Aug. 24, 2018, 1:10 p.m. UTC | #4
On Fri, Aug 24, 2018 at 06:07:22AM -0700, Guenter Roeck wrote:
> On Thu, Aug 23, 2018 at 06:47:09PM +1000, Nicholas Piggin wrote:
> > The generic tlb_end_vma does not call invalidate_range mmu notifier,
> > and it resets resets the mmu_gather range, which means the notifier
> > won't be called on part of the range in case of an unmap that spans
> > multiple vmas.
> > 
> > ARM64 seems to be the only arch I could see that has notifiers and
> > uses the generic tlb_end_vma. I have not actually tested it.
> > 
> > Signed-off-by: Nicholas Piggin <npiggin@gmail.com>
> > Acked-by: Will Deacon <will.deacon@arm.com>
> 
> This patch breaks riscv builds in mainline.

Looks very similar to the breakage we hit on arm64. diff below should fix
it.

Will

--->*

diff --git a/arch/riscv/include/asm/tlb.h b/arch/riscv/include/asm/tlb.h
index c229509288ea..5017060be63c 100644
--- a/arch/riscv/include/asm/tlb.h
+++ b/arch/riscv/include/asm/tlb.h
@@ -14,11 +14,11 @@
 #ifndef _ASM_RISCV_TLB_H
 #define _ASM_RISCV_TLB_H
 
-#include <asm-generic/tlb.h>
-
 static inline void tlb_flush(struct mmu_gather *tlb)
 {
 	flush_tlb_mm(tlb->mm);
 }
 
+#include <asm-generic/tlb.h>
+
 #endif /* _ASM_RISCV_TLB_H */
Guenter Roeck Aug. 24, 2018, 1:24 p.m. UTC | #5
On Fri, Aug 24, 2018 at 02:10:27PM +0100, Will Deacon wrote:
> On Fri, Aug 24, 2018 at 06:07:22AM -0700, Guenter Roeck wrote:
> > On Thu, Aug 23, 2018 at 06:47:09PM +1000, Nicholas Piggin wrote:
> > > The generic tlb_end_vma does not call invalidate_range mmu notifier,
> > > and it resets resets the mmu_gather range, which means the notifier
> > > won't be called on part of the range in case of an unmap that spans
> > > multiple vmas.
> > > 
> > > ARM64 seems to be the only arch I could see that has notifiers and
> > > uses the generic tlb_end_vma. I have not actually tested it.
> > > 
> > > Signed-off-by: Nicholas Piggin <npiggin@gmail.com>
> > > Acked-by: Will Deacon <will.deacon@arm.com>
> > 
> > This patch breaks riscv builds in mainline.
> 
> Looks very similar to the breakage we hit on arm64. diff below should fix
> it.
> 

Unfortunately it doesn't.

In file included from ./arch/riscv/include/asm/pgtable.h:26:0,
                 from ./include/linux/memremap.h:7,
                 from ./include/linux/mm.h:27,
                 from arch/riscv/mm/fault.c:23:
./arch/riscv/include/asm/tlb.h: In function ‘tlb_flush’:
./arch/riscv/include/asm/tlb.h:19:18: error: dereferencing pointer to incomplete type ‘struct mmu_gather’
  flush_tlb_mm(tlb->mm);
                  ^
./arch/riscv/include/asm/tlbflush.h:58:35: note: in definition of macro ‘flush_tlb_mm’
  sbi_remote_sfence_vma(mm_cpumask(mm)->bits, 0, -1)

Note that reverting the offending patch does fix the problem,
so there is no secondary problem lurking around.

Guenter
Will Deacon Aug. 24, 2018, 1:34 p.m. UTC | #6
On Fri, Aug 24, 2018 at 06:24:19AM -0700, Guenter Roeck wrote:
> On Fri, Aug 24, 2018 at 02:10:27PM +0100, Will Deacon wrote:
> > On Fri, Aug 24, 2018 at 06:07:22AM -0700, Guenter Roeck wrote:
> > > On Thu, Aug 23, 2018 at 06:47:09PM +1000, Nicholas Piggin wrote:
> > > > The generic tlb_end_vma does not call invalidate_range mmu notifier,
> > > > and it resets resets the mmu_gather range, which means the notifier
> > > > won't be called on part of the range in case of an unmap that spans
> > > > multiple vmas.
> > > > 
> > > > ARM64 seems to be the only arch I could see that has notifiers and
> > > > uses the generic tlb_end_vma. I have not actually tested it.
> > > > 
> > > > Signed-off-by: Nicholas Piggin <npiggin@gmail.com>
> > > > Acked-by: Will Deacon <will.deacon@arm.com>
> > > 
> > > This patch breaks riscv builds in mainline.
> > 
> > Looks very similar to the breakage we hit on arm64. diff below should fix
> > it.
> > 
> 
> Unfortunately it doesn't.
> 
> In file included from ./arch/riscv/include/asm/pgtable.h:26:0,
>                  from ./include/linux/memremap.h:7,
>                  from ./include/linux/mm.h:27,
>                  from arch/riscv/mm/fault.c:23:
> ./arch/riscv/include/asm/tlb.h: In function ‘tlb_flush’:
> ./arch/riscv/include/asm/tlb.h:19:18: error: dereferencing pointer to incomplete type ‘struct mmu_gather’
>   flush_tlb_mm(tlb->mm);
>                   ^

Sorry, I was a bit quick of the mark there. You'll need a forward
declaration for the paramater type. Here it is with a commit message,
although still untested because I haven't got round to setting up a riscv
toolchain yet.

Will

--->8

From adb9be33d68320edcda80d540a97a647792894d2 Mon Sep 17 00:00:00 2001
From: Will Deacon <will.deacon@arm.com>
Date: Fri, 24 Aug 2018 14:33:48 +0100
Subject: [PATCH] riscv: tlb: Provide definition of tlb_flush() before
 including tlb.h

As of commit fd1102f0aade ("mm: mmu_notifier fix for tlb_end_vma"),
asm-generic/tlb.h now calls tlb_flush() from a static inline function,
so we need to make sure that it's declared before #including the
asm-generic header in the arch header.

Since tlb_flush() is a one-liner for riscv, we can define it before
including asm-generic/tlb.h as long as we provide a forward declaration
of struct mmu_gather.

Reported-by: Guenter Roeck <linux@roeck-us.net>
Signed-off-by: Will Deacon <will.deacon@arm.com>
---
 arch/riscv/include/asm/tlb.h | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/arch/riscv/include/asm/tlb.h b/arch/riscv/include/asm/tlb.h
index c229509288ea..a3d1380ad970 100644
--- a/arch/riscv/include/asm/tlb.h
+++ b/arch/riscv/include/asm/tlb.h
@@ -14,11 +14,13 @@
 #ifndef _ASM_RISCV_TLB_H
 #define _ASM_RISCV_TLB_H
 
-#include <asm-generic/tlb.h>
+struct mmu_gather;
 
 static inline void tlb_flush(struct mmu_gather *tlb)
 {
 	flush_tlb_mm(tlb->mm);
 }
 
+#include <asm-generic/tlb.h>
+
 #endif /* _ASM_RISCV_TLB_H */
Will Deacon Aug. 24, 2018, 1:50 p.m. UTC | #7
On Fri, Aug 24, 2018 at 02:34:27PM +0100, Will Deacon wrote:
> On Fri, Aug 24, 2018 at 06:24:19AM -0700, Guenter Roeck wrote:
> > On Fri, Aug 24, 2018 at 02:10:27PM +0100, Will Deacon wrote:
> > > On Fri, Aug 24, 2018 at 06:07:22AM -0700, Guenter Roeck wrote:
> > > > On Thu, Aug 23, 2018 at 06:47:09PM +1000, Nicholas Piggin wrote:
> > > > > The generic tlb_end_vma does not call invalidate_range mmu notifier,
> > > > > and it resets resets the mmu_gather range, which means the notifier
> > > > > won't be called on part of the range in case of an unmap that spans
> > > > > multiple vmas.
> > > > > 
> > > > > ARM64 seems to be the only arch I could see that has notifiers and
> > > > > uses the generic tlb_end_vma. I have not actually tested it.
> > > > > 
> > > > > Signed-off-by: Nicholas Piggin <npiggin@gmail.com>
> > > > > Acked-by: Will Deacon <will.deacon@arm.com>
> > > > 
> > > > This patch breaks riscv builds in mainline.
> > > 
> > > Looks very similar to the breakage we hit on arm64. diff below should fix
> > > it.
> > > 
> > 
> > Unfortunately it doesn't.
> > 
> > In file included from ./arch/riscv/include/asm/pgtable.h:26:0,
> >                  from ./include/linux/memremap.h:7,
> >                  from ./include/linux/mm.h:27,
> >                  from arch/riscv/mm/fault.c:23:
> > ./arch/riscv/include/asm/tlb.h: In function ‘tlb_flush’:
> > ./arch/riscv/include/asm/tlb.h:19:18: error: dereferencing pointer to incomplete type ‘struct mmu_gather’
> >   flush_tlb_mm(tlb->mm);
> >                   ^
> 
> Sorry, I was a bit quick of the mark there. You'll need a forward
> declaration for the paramater type. Here it is with a commit message,
> although still untested because I haven't got round to setting up a riscv
> toolchain yet.
> 
> Will
> 
> --->8
> 
> From adb9be33d68320edcda80d540a97a647792894d2 Mon Sep 17 00:00:00 2001
> From: Will Deacon <will.deacon@arm.com>
> Date: Fri, 24 Aug 2018 14:33:48 +0100
> Subject: [PATCH] riscv: tlb: Provide definition of tlb_flush() before
>  including tlb.h
> 
> As of commit fd1102f0aade ("mm: mmu_notifier fix for tlb_end_vma"),
> asm-generic/tlb.h now calls tlb_flush() from a static inline function,
> so we need to make sure that it's declared before #including the
> asm-generic header in the arch header.
> 
> Since tlb_flush() is a one-liner for riscv, we can define it before
> including asm-generic/tlb.h as long as we provide a forward declaration
> of struct mmu_gather.
> 
> Reported-by: Guenter Roeck <linux@roeck-us.net>
> Signed-off-by: Will Deacon <will.deacon@arm.com>
> ---
>  arch/riscv/include/asm/tlb.h | 4 +++-
>  1 file changed, 3 insertions(+), 1 deletion(-)
> 
> diff --git a/arch/riscv/include/asm/tlb.h b/arch/riscv/include/asm/tlb.h
> index c229509288ea..a3d1380ad970 100644
> --- a/arch/riscv/include/asm/tlb.h
> +++ b/arch/riscv/include/asm/tlb.h
> @@ -14,11 +14,13 @@
>  #ifndef _ASM_RISCV_TLB_H
>  #define _ASM_RISCV_TLB_H
>  
> -#include <asm-generic/tlb.h>
> +struct mmu_gather;
>  
>  static inline void tlb_flush(struct mmu_gather *tlb)
>  {
>  	flush_tlb_mm(tlb->mm);

Bah, didn't spot the dereference so this won't work either. You basically
just need to copy what I did for arm64 in d475fac95779.

Will
Guenter Roeck Aug. 24, 2018, 1:54 p.m. UTC | #8
On Fri, Aug 24, 2018 at 02:50:48PM +0100, Will Deacon wrote:
> > 
> > Sorry, I was a bit quick of the mark there. You'll need a forward
> > declaration for the paramater type. Here it is with a commit message,
> > although still untested because I haven't got round to setting up a riscv
> > toolchain yet.
> > 

Still doesn't work.

CC      mm/memory.o
In file included from ./arch/riscv/include/asm/pgtable.h:26:0,
                 from ./include/linux/memremap.h:7,
		 from ./include/linux/mm.h:27,
		 from arch/riscv/mm/fault.c:23:
./arch/riscv/include/asm/tlb.h: In function ‘tlb_flush’:
./arch/riscv/include/asm/tlb.h:21:18: error:
	dereferencing pointer to incomplete type ‘struct mmu_gather’ flush_tlb_mm(tlb->mm);

Problem is that struct mmu_gather is dereferenced in tlb_flush().

Guenter

> > Will
> > 
> > --->8
> > 
> > From adb9be33d68320edcda80d540a97a647792894d2 Mon Sep 17 00:00:00 2001
> > From: Will Deacon <will.deacon@arm.com>
> > Date: Fri, 24 Aug 2018 14:33:48 +0100
> > Subject: [PATCH] riscv: tlb: Provide definition of tlb_flush() before
> >  including tlb.h
> > 
> > As of commit fd1102f0aade ("mm: mmu_notifier fix for tlb_end_vma"),
> > asm-generic/tlb.h now calls tlb_flush() from a static inline function,
> > so we need to make sure that it's declared before #including the
> > asm-generic header in the arch header.
> > 
> > Since tlb_flush() is a one-liner for riscv, we can define it before
> > including asm-generic/tlb.h as long as we provide a forward declaration
> > of struct mmu_gather.
> > 
> > Reported-by: Guenter Roeck <linux@roeck-us.net>
> > Signed-off-by: Will Deacon <will.deacon@arm.com>
> > ---
> >  arch/riscv/include/asm/tlb.h | 4 +++-
> >  1 file changed, 3 insertions(+), 1 deletion(-)
> > 
> > diff --git a/arch/riscv/include/asm/tlb.h b/arch/riscv/include/asm/tlb.h
> > index c229509288ea..a3d1380ad970 100644
> > --- a/arch/riscv/include/asm/tlb.h
> > +++ b/arch/riscv/include/asm/tlb.h
> > @@ -14,11 +14,13 @@
> >  #ifndef _ASM_RISCV_TLB_H
> >  #define _ASM_RISCV_TLB_H
> >  
> > -#include <asm-generic/tlb.h>
> > +struct mmu_gather;
> >  
> >  static inline void tlb_flush(struct mmu_gather *tlb)
> >  {
> >  	flush_tlb_mm(tlb->mm);
> 
> Bah, didn't spot the dereference so this won't work either. You basically
> just need to copy what I did for arm64 in d475fac95779.
> 
> Will
Guenter Roeck Aug. 24, 2018, 2:06 p.m. UTC | #9
On 08/24/2018 06:50 AM, Will Deacon wrote:

>> -#include <asm-generic/tlb.h>
>> +struct mmu_gather;
>>   
>>   static inline void tlb_flush(struct mmu_gather *tlb)
>>   {
>>   	flush_tlb_mm(tlb->mm);
> 
> Bah, didn't spot the dereference so this won't work either. You basically
> just need to copy what I did for arm64 in d475fac95779.
> 

Yes, this seems to work. It doesn't really need "struct mmu_gather;" -
I assume that is included from elsewhere - but I added it to be safe.

Can you send a full patch, or do you want me to do it ?

Thanks,
Guenter

---
diff --git a/arch/riscv/include/asm/tlb.h b/arch/riscv/include/asm/tlb.h
index c229509288ea..439dc7072e05 100644
--- a/arch/riscv/include/asm/tlb.h
+++ b/arch/riscv/include/asm/tlb.h
@@ -14,6 +14,10 @@
  #ifndef _ASM_RISCV_TLB_H
  #define _ASM_RISCV_TLB_H

+struct mmu_gather;
+
+static void tlb_flush(struct mmu_gather *tlb);
+
  #include <asm-generic/tlb.h>

  static inline void tlb_flush(struct mmu_gather *tlb)
Will Deacon Aug. 24, 2018, 2:25 p.m. UTC | #10
On Fri, Aug 24, 2018 at 07:06:51AM -0700, Guenter Roeck wrote:
> On 08/24/2018 06:50 AM, Will Deacon wrote:
> 
> >>-#include <asm-generic/tlb.h>
> >>+struct mmu_gather;
> >>  static inline void tlb_flush(struct mmu_gather *tlb)
> >>  {
> >>  	flush_tlb_mm(tlb->mm);
> >
> >Bah, didn't spot the dereference so this won't work either. You basically
> >just need to copy what I did for arm64 in d475fac95779.
> >
> 
> Yes, this seems to work. It doesn't really need "struct mmu_gather;" -
> I assume that is included from elsewhere - but I added it to be safe.

struct mmu_gather comes in via asm-generic/tlb.h.

> Can you send a full patch, or do you want me to do it ?

I'm evidently incapable of writing code today, so please go ahead :)

Will
Guenter Roeck Aug. 24, 2018, 6:22 p.m. UTC | #11
On Fri, Aug 24, 2018 at 03:25:33PM +0100, Will Deacon wrote:
> On Fri, Aug 24, 2018 at 07:06:51AM -0700, Guenter Roeck wrote:
> > On 08/24/2018 06:50 AM, Will Deacon wrote:
> > 
> > >>-#include <asm-generic/tlb.h>
> > >>+struct mmu_gather;
> > >>  static inline void tlb_flush(struct mmu_gather *tlb)
> > >>  {
> > >>  	flush_tlb_mm(tlb->mm);
> > >
> > >Bah, didn't spot the dereference so this won't work either. You basically
> > >just need to copy what I did for arm64 in d475fac95779.
> > >
> > 
> > Yes, this seems to work. It doesn't really need "struct mmu_gather;" -
> > I assume that is included from elsewhere - but I added it to be safe.
> 
> struct mmu_gather comes in via asm-generic/tlb.h.
> 
From linux/mm.h, really, which happens to be included before
asm/tlb.h is included (see arch/riscv/include/asm/pgalloc.h).
I kept it to be future-proof.

> > Can you send a full patch, or do you want me to do it ?
> 
> I'm evidently incapable of writing code today, so please go ahead :)
> 
Done. We'll see if I am any better.

Guenter
Palmer Dabbelt Aug. 24, 2018, 11:32 p.m. UTC | #12
On Fri, 24 Aug 2018 06:50:48 PDT (-0700), Will Deacon wrote:
> On Fri, Aug 24, 2018 at 02:34:27PM +0100, Will Deacon wrote:
>> On Fri, Aug 24, 2018 at 06:24:19AM -0700, Guenter Roeck wrote:
>> > On Fri, Aug 24, 2018 at 02:10:27PM +0100, Will Deacon wrote:
>> > > On Fri, Aug 24, 2018 at 06:07:22AM -0700, Guenter Roeck wrote:
>> > > > On Thu, Aug 23, 2018 at 06:47:09PM +1000, Nicholas Piggin wrote:
>> > > > > The generic tlb_end_vma does not call invalidate_range mmu notifier,
>> > > > > and it resets resets the mmu_gather range, which means the notifier
>> > > > > won't be called on part of the range in case of an unmap that spans
>> > > > > multiple vmas.
>> > > > >
>> > > > > ARM64 seems to be the only arch I could see that has notifiers and
>> > > > > uses the generic tlb_end_vma. I have not actually tested it.
>> > > > >
>> > > > > Signed-off-by: Nicholas Piggin <npiggin@gmail.com>
>> > > > > Acked-by: Will Deacon <will.deacon@arm.com>
>> > > >
>> > > > This patch breaks riscv builds in mainline.
>> > >
>> > > Looks very similar to the breakage we hit on arm64. diff below should fix
>> > > it.
>> > >
>> >
>> > Unfortunately it doesn't.
>> >
>> > In file included from ./arch/riscv/include/asm/pgtable.h:26:0,
>> >                  from ./include/linux/memremap.h:7,
>> >                  from ./include/linux/mm.h:27,
>> >                  from arch/riscv/mm/fault.c:23:
>> > ./arch/riscv/include/asm/tlb.h: In function ‘tlb_flush’:
>> > ./arch/riscv/include/asm/tlb.h:19:18: error: dereferencing pointer to incomplete type ‘struct mmu_gather’
>> >   flush_tlb_mm(tlb->mm);
>> >                   ^
>>
>> Sorry, I was a bit quick of the mark there. You'll need a forward
>> declaration for the paramater type. Here it is with a commit message,
>> although still untested because I haven't got round to setting up a riscv
>> toolchain yet.

FWIW, Arnd built them last time he updated the cross tools so you should be 
able to get GCC 8.1.0 for RISC-V from there.  I use this make.cross script that 
I stole from the Intel 0-day robot

    https://github.com/palmer-dabbelt/home/blob/master/.local/src/local-scripts/make.cross.bash

If I'm reading it correctly the tools come from here

    http://cdn.kernel.org/pub/tools/crosstool/files/bin/x86_64/8.1.0/x86_64-gcc-8.1.0-nolibc-riscv64-linux.tar.gz

I use the make.cross script as it makes it super easy to test my 
across-the-tree patches on other people's ports.

>>
>> Will
>>
>> --->8
>>
>> From adb9be33d68320edcda80d540a97a647792894d2 Mon Sep 17 00:00:00 2001
>> From: Will Deacon <will.deacon@arm.com>
>> Date: Fri, 24 Aug 2018 14:33:48 +0100
>> Subject: [PATCH] riscv: tlb: Provide definition of tlb_flush() before
>>  including tlb.h
>>
>> As of commit fd1102f0aade ("mm: mmu_notifier fix for tlb_end_vma"),
>> asm-generic/tlb.h now calls tlb_flush() from a static inline function,
>> so we need to make sure that it's declared before #including the
>> asm-generic header in the arch header.
>>
>> Since tlb_flush() is a one-liner for riscv, we can define it before
>> including asm-generic/tlb.h as long as we provide a forward declaration
>> of struct mmu_gather.
>>
>> Reported-by: Guenter Roeck <linux@roeck-us.net>
>> Signed-off-by: Will Deacon <will.deacon@arm.com>
>> ---
>>  arch/riscv/include/asm/tlb.h | 4 +++-
>>  1 file changed, 3 insertions(+), 1 deletion(-)
>>
>> diff --git a/arch/riscv/include/asm/tlb.h b/arch/riscv/include/asm/tlb.h
>> index c229509288ea..a3d1380ad970 100644
>> --- a/arch/riscv/include/asm/tlb.h
>> +++ b/arch/riscv/include/asm/tlb.h
>> @@ -14,11 +14,13 @@
>>  #ifndef _ASM_RISCV_TLB_H
>>  #define _ASM_RISCV_TLB_H
>>
>> -#include <asm-generic/tlb.h>
>> +struct mmu_gather;
>>
>>  static inline void tlb_flush(struct mmu_gather *tlb)
>>  {
>>  	flush_tlb_mm(tlb->mm);
>
> Bah, didn't spot the dereference so this won't work either. You basically
> just need to copy what I did for arm64 in d475fac95779.
>
> Will
diff mbox series

Patch

diff --git a/include/asm-generic/tlb.h b/include/asm-generic/tlb.h
index e811ef7b8350..79cb76b89c26 100644
--- a/include/asm-generic/tlb.h
+++ b/include/asm-generic/tlb.h
@@ -15,6 +15,7 @@ 
 #ifndef _ASM_GENERIC__TLB_H
 #define _ASM_GENERIC__TLB_H
 
+#include <linux/mmu_notifier.h>
 #include <linux/swap.h>
 #include <asm/pgalloc.h>
 #include <asm/tlbflush.h>
@@ -138,6 +139,16 @@  static inline void __tlb_reset_range(struct mmu_gather *tlb)
 	}
 }
 
+static inline void tlb_flush_mmu_tlbonly(struct mmu_gather *tlb)
+{
+	if (!tlb->end)
+		return;
+
+	tlb_flush(tlb);
+	mmu_notifier_invalidate_range(tlb->mm, tlb->start, tlb->end);
+	__tlb_reset_range(tlb);
+}
+
 static inline void tlb_remove_page_size(struct mmu_gather *tlb,
 					struct page *page, int page_size)
 {
@@ -186,10 +197,8 @@  static inline void tlb_remove_check_page_size_change(struct mmu_gather *tlb,
 
 #define __tlb_end_vma(tlb, vma)					\
 	do {							\
-		if (!tlb->fullmm && tlb->end) {			\
-			tlb_flush(tlb);				\
-			__tlb_reset_range(tlb);			\
-		}						\
+		if (!tlb->fullmm)				\
+			tlb_flush_mmu_tlbonly(tlb);		\
 	} while (0)
 
 #ifndef tlb_end_vma
diff --git a/mm/memory.c b/mm/memory.c
index 7c58310734eb..c4a7b6cb17c8 100644
--- a/mm/memory.c
+++ b/mm/memory.c
@@ -238,16 +238,6 @@  void arch_tlb_gather_mmu(struct mmu_gather *tlb, struct mm_struct *mm,
 	__tlb_reset_range(tlb);
 }
 
-static void tlb_flush_mmu_tlbonly(struct mmu_gather *tlb)
-{
-	if (!tlb->end)
-		return;
-
-	tlb_flush(tlb);
-	mmu_notifier_invalidate_range(tlb->mm, tlb->start, tlb->end);
-	__tlb_reset_range(tlb);
-}
-
 static void tlb_flush_mmu_free(struct mmu_gather *tlb)
 {
 	struct mmu_gather_batch *batch;