| From 01e67e04c28170c47700c2c226d732bbfedb1ad0 Mon Sep 17 00:00:00 2001 |
| From: Paolo Bonzini <pbonzini@redhat.com> |
| Date: Fri, 8 Apr 2022 13:09:04 -0700 |
| Subject: mmmremap.c: avoid pointless invalidate_range_start/end on mremap(old_size=0) |
| |
| From: Paolo Bonzini <pbonzini@redhat.com> |
| |
| commit 01e67e04c28170c47700c2c226d732bbfedb1ad0 upstream. |
| |
| If an mremap() syscall with old_size=0 ends up in move_page_tables(), it |
| will call invalidate_range_start()/invalidate_range_end() unnecessarily, |
| i.e. with an empty range. |
| |
| This causes a WARN in KVM's mmu_notifier. In the past, empty ranges |
| have been diagnosed to be off-by-one bugs, hence the WARNing. Given the |
| low (so far) number of unique reports, the benefits of detecting more |
| buggy callers seem to outweigh the cost of having to fix cases such as |
| this one, where userspace is doing something silly. In this particular |
| case, an early return from move_page_tables() is enough to fix the |
| issue. |
| |
| Link: https://lkml.kernel.org/r/20220329173155.172439-1-pbonzini@redhat.com |
| Reported-by: syzbot+6bde52d89cfdf9f61425@syzkaller.appspotmail.com |
| Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> |
| Cc: Sean Christopherson <seanjc@google.com> |
| Cc: <stable@vger.kernel.org> |
| Signed-off-by: Andrew Morton <akpm@linux-foundation.org> |
| Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org> |
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |
| --- |
| mm/mremap.c | 3 +++ |
| 1 file changed, 3 insertions(+) |
| |
| --- a/mm/mremap.c |
| +++ b/mm/mremap.c |
| @@ -486,6 +486,9 @@ unsigned long move_page_tables(struct vm |
| pmd_t *old_pmd, *new_pmd; |
| pud_t *old_pud, *new_pud; |
| |
| + if (!len) |
| + return 0; |
| + |
| old_end = old_addr + len; |
| flush_cache_range(vma, old_addr, old_end); |
| |