[Devel] [PATCH 02/11] x86/mm: Support mremap()'ing vdso vma
Dmitry Safonov
dsafonov at virtuozzo.com
Thu May 18 11:39:41 PDT 2017
CRIU needs remapping vdso blob on restore. It moves vdso vma to the same
position as it was on checkpoint with mremap() call.
During mremap() the position of vma is changed with the result that
current->mm->context.vdso pointer is no longer valid.
By chance 64-bit signal processing code doesn't need context.vdso
pointer for landing. But it's needed for ia32 signals.
This is quite ugly backport of ms commit commit b059a453b1cf
("x86/vdso: Add mremap hook to vm_special_mapping").
As vdso code was rewritten in ~3.16 kernel, it can't be backported
as-is and here is the simplest result for the kernel which has
no struct vm_special_mapping yet.
Signed-off-by: Dmitry Safonov <dsafonov at virtuozzo.com>
---
arch/x86/include/asm/Kbuild | 1 -
arch/x86/include/asm/mm-arch-hooks.h | 20 ++++++++++++++++++++
arch/x86/vdso/vdso32-setup.c | 18 ++++++++++++++++++
3 files changed, 38 insertions(+), 1 deletion(-)
create mode 100644 arch/x86/include/asm/mm-arch-hooks.h
diff --git a/arch/x86/include/asm/Kbuild b/arch/x86/include/asm/Kbuild
index 6ae17f59eaf3..7f669853317a 100644
--- a/arch/x86/include/asm/Kbuild
+++ b/arch/x86/include/asm/Kbuild
@@ -5,4 +5,3 @@ genhdr-y += unistd_64.h
genhdr-y += unistd_x32.h
generic-y += clkdev.h
-generic-y += mm-arch-hooks.h
diff --git a/arch/x86/include/asm/mm-arch-hooks.h b/arch/x86/include/asm/mm-arch-hooks.h
new file mode 100644
index 000000000000..64fb20ad511d
--- /dev/null
+++ b/arch/x86/include/asm/mm-arch-hooks.h
@@ -0,0 +1,20 @@
+/*
+ * Architecture specific mm hooks
+ *
+ * Copyright (C) 2015, IBM Corporation
+ * Author: Laurent Dufour <ldufour at linux.vnet.ibm.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ */
+
+#ifndef _ASM_POWERPC_MM_ARCH_HOOKS_H
+#define _ASM_POWERPC_MM_ARCH_HOOKS_H
+
+extern 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 /* _ASM_POWERPC_MM_ARCH_HOOKS_H */
diff --git a/arch/x86/vdso/vdso32-setup.c b/arch/x86/vdso/vdso32-setup.c
index 59ec0e2ebee0..776face0d979 100644
--- a/arch/x86/vdso/vdso32-setup.c
+++ b/arch/x86/vdso/vdso32-setup.c
@@ -416,6 +416,24 @@ out:
return pages;
}
+void arch_remap(struct mm_struct *mm,
+ unsigned long old_start, unsigned long old_end,
+ unsigned long new_start, unsigned long new_end)
+{
+ /*
+ * mremap() doesn't allow moving multiple vmas so we can limit the
+ * check to old_start == vdso_base.
+ */
+ if (old_start == (unsigned long)mm->context.vdso) {
+ if (WARN_ON_ONCE(current->mm != mm))
+ return;
+
+ mm->context.vdso = (void *)new_start;
+ current_thread_info()->sysenter_return =
+ VDSO32_SYMBOL(new_start, SYSENTER_RETURN);
+ }
+}
+
/* Call under mm->mmap_sem */
static int __arch_setup_additional_pages(unsigned long addr, bool compat)
{
--
2.12.2
More information about the Devel
mailing list