Some architecture would like to be triggered when a memory area is moved
through the mremap system call.

This patch is introducing a new arch_remap mm hook which is placed in the
path of mremap, and is called before the old area is unmapped (and the
arch_unmap hook is called).

Signed-off-by: Laurent Dufour <lduf...@linux.vnet.ibm.com>
---
 include/linux/mm-arch-hooks.h |  9 +++++++++
 mm/mremap.c                   | 17 +++++++++++------
 2 files changed, 20 insertions(+), 6 deletions(-)

diff --git a/include/linux/mm-arch-hooks.h b/include/linux/mm-arch-hooks.h
index 63005e367abd..4efc3f56e6df 100644
--- a/include/linux/mm-arch-hooks.h
+++ b/include/linux/mm-arch-hooks.h
@@ -13,4 +13,13 @@
 
 #include <asm/mm-arch-hooks.h>
 
+#ifndef arch_remap
+static inline void arch_remap(struct mm_struct *mm,
+                             unsigned long old_start, unsigned long old_end,
+                             unsigned long new_start, unsigned long new_end)
+{
+}
+#define arch_remap arch_remap
+#endif
+
 #endif /* _LINUX_MM_ARCH_HOOKS_H */
diff --git a/mm/mremap.c b/mm/mremap.c
index 2dc44b1cb1df..7597af900d07 100644
--- a/mm/mremap.c
+++ b/mm/mremap.c
@@ -22,6 +22,7 @@
 #include <linux/mmu_notifier.h>
 #include <linux/sched/sysctl.h>
 #include <linux/uaccess.h>
+#include <linux/mm-arch-hooks.h>
 
 #include <asm/cacheflush.h>
 #include <asm/tlbflush.h>
@@ -286,13 +287,17 @@ static unsigned long move_vma(struct vm_area_struct *vma,
                old_len = new_len;
                old_addr = new_addr;
                new_addr = -ENOMEM;
-       } else if (vma->vm_file && vma->vm_file->f_op->mremap) {
-               err = vma->vm_file->f_op->mremap(vma->vm_file, new_vma);
-               if (err < 0) {
-                       move_page_tables(new_vma, new_addr, vma, old_addr,
-                                        moved_len, true);
-                       return err;
+       } else {
+               if (vma->vm_file && vma->vm_file->f_op->mremap) {
+                       err = vma->vm_file->f_op->mremap(vma->vm_file, new_vma);
+                       if (err < 0) {
+                               move_page_tables(new_vma, new_addr, vma,
+                                                old_addr, moved_len, true);
+                               return err;
+                       }
                }
+               arch_remap(mm, old_addr, old_addr + old_len,
+                          new_addr, new_addr + new_len);
        }
 
        /* Conceal VM_ACCOUNT so old reservation is not undone */
-- 
1.9.1

_______________________________________________
Linuxppc-dev mailing list
Linuxppc-dev@lists.ozlabs.org
https://lists.ozlabs.org/listinfo/linuxppc-dev

Reply via email to