[v7,6/7] mm/madvise: employ mmget_still_valid for write lock
diff mbox series

Message ID 20200302193630.68771-7-minchan@kernel.org
State In Next
Commit d70f08c083d51c1016fa62b7073dc14214f470b5
Headers show
Series
  • introduce memory hinting API for external process
Related show

Commit Message

Minchan Kim March 2, 2020, 7:36 p.m. UTC
From: Oleksandr Natalenko <oleksandr@redhat.com>

Do the very same trick as we already do since 04f5866e41fb. KSM hints
will require locking mmap_sem for write since they modify vm_flags, so
for remote KSM hinting this additional check is needed.

Reviewed-by: Suren Baghdasaryan <surenb@google.com>
Signed-off-by: Oleksandr Natalenko <oleksandr@redhat.com>
Signed-off-by: Minchan Kim <minchan@kernel.org>
---
 mm/madvise.c | 3 +++
 1 file changed, 3 insertions(+)

Comments

Vlastimil Babka March 6, 2020, 12:52 p.m. UTC | #1
On 3/2/20 8:36 PM, Minchan Kim wrote:
> From: Oleksandr Natalenko <oleksandr@redhat.com>
> 
> Do the very same trick as we already do since 04f5866e41fb. KSM hints
> will require locking mmap_sem for write since they modify vm_flags, so
> for remote KSM hinting this additional check is needed.
> 
> Reviewed-by: Suren Baghdasaryan <surenb@google.com>
> Signed-off-by: Oleksandr Natalenko <oleksandr@redhat.com>
> Signed-off-by: Minchan Kim <minchan@kernel.org>
> ---
>  mm/madvise.c | 3 +++
>  1 file changed, 3 insertions(+)
> 
> diff --git a/mm/madvise.c b/mm/madvise.c
> index e794367f681e..e77c6c1fad34 100644
> --- a/mm/madvise.c
> +++ b/mm/madvise.c
> @@ -1118,6 +1118,8 @@ int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
>  	if (write) {
>  		if (down_write_killable(&mm->mmap_sem))
>  			return -EINTR;
> +		if (current->mm != mm && !mmget_still_valid(mm))
> +			goto skip_mm;

This will return 0, is that correct? Shoudln't there be a similar error e.g. as
when finding the task by pid fails (-ESRCH ?), because IIUC the task here is
going away and dumping the core?

>  	} else {
>  		down_read(&mm->mmap_sem);
>  	}
> @@ -1169,6 +1171,7 @@ int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
>  	}
>  out:
>  	blk_finish_plug(&plug);
> +skip_mm:
>  	if (write)
>  		up_write(&mm->mmap_sem);
>  	else
>
Oleksandr Natalenko March 6, 2020, 1:03 p.m. UTC | #2
Hello.

On Fri, Mar 06, 2020 at 01:52:07PM +0100, Vlastimil Babka wrote:
> > diff --git a/mm/madvise.c b/mm/madvise.c
> > index e794367f681e..e77c6c1fad34 100644
> > --- a/mm/madvise.c
> > +++ b/mm/madvise.c
> > @@ -1118,6 +1118,8 @@ int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
> >  	if (write) {
> >  		if (down_write_killable(&mm->mmap_sem))
> >  			return -EINTR;
> > +		if (current->mm != mm && !mmget_still_valid(mm))
> > +			goto skip_mm;
> 
> This will return 0, is that correct? Shoudln't there be a similar error e.g. as
> when finding the task by pid fails (-ESRCH ?), because IIUC the task here is
> going away and dumping the core?

Yeah.

Something like this then:

===
diff --git a/mm/madvise.c b/mm/madvise.c
index 48d1da08c160..7ed2f4d13924 100644
--- a/mm/madvise.c
+++ b/mm/madvise.c
@@ -1122,6 +1122,10 @@ int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
 	if (write) {
 		if (down_write_killable(&mm->mmap_sem))
 			return -EINTR;
+		if (current->mm != mm && !mmget_still_valid(mm)) {
+			error = -ESRCH;
+			goto skip_mm;
+		}
 	} else {
 		down_read(&mm->mmap_sem);
 	}
@@ -1173,6 +1177,7 @@ int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
 	}
 out:
 	blk_finish_plug(&plug);
+skip_mm:
 	if (write)
 		up_write(&mm->mmap_sem);
 	else

===

?

> 
> >  	} else {
> >  		down_read(&mm->mmap_sem);
> >  	}
> > @@ -1169,6 +1171,7 @@ int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
> >  	}
> >  out:
> >  	blk_finish_plug(&plug);
> > +skip_mm:
> >  	if (write)
> >  		up_write(&mm->mmap_sem);
> >  	else
> > 
>
Vlastimil Babka March 6, 2020, 4:03 p.m. UTC | #3
On 3/6/20 2:03 PM, Oleksandr Natalenko wrote:
> Hello.
> 
> On Fri, Mar 06, 2020 at 01:52:07PM +0100, Vlastimil Babka wrote:
>> > diff --git a/mm/madvise.c b/mm/madvise.c
>> > index e794367f681e..e77c6c1fad34 100644
>> > --- a/mm/madvise.c
>> > +++ b/mm/madvise.c
>> > @@ -1118,6 +1118,8 @@ int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
>> >  	if (write) {
>> >  		if (down_write_killable(&mm->mmap_sem))
>> >  			return -EINTR;
>> > +		if (current->mm != mm && !mmget_still_valid(mm))
>> > +			goto skip_mm;
>> 
>> This will return 0, is that correct? Shoudln't there be a similar error e.g. as
>> when finding the task by pid fails (-ESRCH ?), because IIUC the task here is
>> going away and dumping the core?
> 
> Yeah.
> 
> Something like this then:
> 
> ===
> diff --git a/mm/madvise.c b/mm/madvise.c
> index 48d1da08c160..7ed2f4d13924 100644
> --- a/mm/madvise.c
> +++ b/mm/madvise.c
> @@ -1122,6 +1122,10 @@ int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
>  	if (write) {
>  		if (down_write_killable(&mm->mmap_sem))
>  			return -EINTR;
> +		if (current->mm != mm && !mmget_still_valid(mm)) {
> +			error = -ESRCH;
> +			goto skip_mm;
> +		}
>  	} else {
>  		down_read(&mm->mmap_sem);
>  	}
> @@ -1173,6 +1177,7 @@ int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
>  	}
>  out:
>  	blk_finish_plug(&plug);
> +skip_mm:
>  	if (write)
>  		up_write(&mm->mmap_sem);
>  	else
> 
> ===
> 
> ?

Yep, thanks.
Oleksandr Natalenko March 9, 2020, 12:30 p.m. UTC | #4
On Fri, Mar 06, 2020 at 05:03:50PM +0100, Vlastimil Babka wrote:
> On 3/6/20 2:03 PM, Oleksandr Natalenko wrote:
> > Hello.
> > 
> > On Fri, Mar 06, 2020 at 01:52:07PM +0100, Vlastimil Babka wrote:
> >> > diff --git a/mm/madvise.c b/mm/madvise.c
> >> > index e794367f681e..e77c6c1fad34 100644
> >> > --- a/mm/madvise.c
> >> > +++ b/mm/madvise.c
> >> > @@ -1118,6 +1118,8 @@ int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
> >> >  	if (write) {
> >> >  		if (down_write_killable(&mm->mmap_sem))
> >> >  			return -EINTR;
> >> > +		if (current->mm != mm && !mmget_still_valid(mm))
> >> > +			goto skip_mm;
> >> 
> >> This will return 0, is that correct? Shoudln't there be a similar error e.g. as
> >> when finding the task by pid fails (-ESRCH ?), because IIUC the task here is
> >> going away and dumping the core?
> > 
> > Yeah.
> > 
> > Something like this then:
> > 
> > ===
> > diff --git a/mm/madvise.c b/mm/madvise.c
> > index 48d1da08c160..7ed2f4d13924 100644
> > --- a/mm/madvise.c
> > +++ b/mm/madvise.c
> > @@ -1122,6 +1122,10 @@ int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
> >  	if (write) {
> >  		if (down_write_killable(&mm->mmap_sem))
> >  			return -EINTR;
> > +		if (current->mm != mm && !mmget_still_valid(mm)) {
> > +			error = -ESRCH;
> > +			goto skip_mm;
> > +		}
> >  	} else {
> >  		down_read(&mm->mmap_sem);
> >  	}
> > @@ -1173,6 +1177,7 @@ int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
> >  	}
> >  out:
> >  	blk_finish_plug(&plug);
> > +skip_mm:
> >  	if (write)
> >  		up_write(&mm->mmap_sem);
> >  	else
> > 
> > ===
> > 
> > ?
> 
> Yep, thanks.
> 

Minchan, shall you take this change into the next submission, or you'd
prefer me sending it to you as a new patch?
Minchan Kim March 10, 2020, 10:28 p.m. UTC | #5
On Mon, Mar 09, 2020 at 01:30:45PM +0100, Oleksandr Natalenko wrote:
> On Fri, Mar 06, 2020 at 05:03:50PM +0100, Vlastimil Babka wrote:
> > On 3/6/20 2:03 PM, Oleksandr Natalenko wrote:
> > > Hello.
> > > 
> > > On Fri, Mar 06, 2020 at 01:52:07PM +0100, Vlastimil Babka wrote:
> > >> > diff --git a/mm/madvise.c b/mm/madvise.c
> > >> > index e794367f681e..e77c6c1fad34 100644
> > >> > --- a/mm/madvise.c
> > >> > +++ b/mm/madvise.c
> > >> > @@ -1118,6 +1118,8 @@ int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
> > >> >  	if (write) {
> > >> >  		if (down_write_killable(&mm->mmap_sem))
> > >> >  			return -EINTR;
> > >> > +		if (current->mm != mm && !mmget_still_valid(mm))
> > >> > +			goto skip_mm;
> > >> 
> > >> This will return 0, is that correct? Shoudln't there be a similar error e.g. as
> > >> when finding the task by pid fails (-ESRCH ?), because IIUC the task here is
> > >> going away and dumping the core?
> > > 
> > > Yeah.
> > > 
> > > Something like this then:
> > > 
> > > ===
> > > diff --git a/mm/madvise.c b/mm/madvise.c
> > > index 48d1da08c160..7ed2f4d13924 100644
> > > --- a/mm/madvise.c
> > > +++ b/mm/madvise.c
> > > @@ -1122,6 +1122,10 @@ int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
> > >  	if (write) {
> > >  		if (down_write_killable(&mm->mmap_sem))
> > >  			return -EINTR;
> > > +		if (current->mm != mm && !mmget_still_valid(mm)) {
> > > +			error = -ESRCH;
> > > +			goto skip_mm;
> > > +		}
> > >  	} else {
> > >  		down_read(&mm->mmap_sem);
> > >  	}
> > > @@ -1173,6 +1177,7 @@ int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
> > >  	}
> > >  out:
> > >  	blk_finish_plug(&plug);
> > > +skip_mm:
> > >  	if (write)
> > >  		up_write(&mm->mmap_sem);
> > >  	else
> > > 
> > > ===
> > > 
> > > ?
> > 
> > Yep, thanks.
> > 
> 
> Minchan, shall you take this change into the next submission, or you'd
> prefer me sending it to you as a new patch?

I should send patchset again so I will take it.
Thanks!

Patch
diff mbox series

diff --git a/mm/madvise.c b/mm/madvise.c
index e794367f681e..e77c6c1fad34 100644
--- a/mm/madvise.c
+++ b/mm/madvise.c
@@ -1118,6 +1118,8 @@  int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
 	if (write) {
 		if (down_write_killable(&mm->mmap_sem))
 			return -EINTR;
+		if (current->mm != mm && !mmget_still_valid(mm))
+			goto skip_mm;
 	} else {
 		down_read(&mm->mmap_sem);
 	}
@@ -1169,6 +1171,7 @@  int do_madvise(struct task_struct *target_task, struct mm_struct *mm,
 	}
 out:
 	blk_finish_plug(&plug);
+skip_mm:
 	if (write)
 		up_write(&mm->mmap_sem);
 	else