linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH v4 01/10] mm: Allow arch specific arch_randomize_brk() with CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT
  2021-12-08 17:18 [PATCH v4 00/10] Convert powerpc to default topdown mmap layout Christophe Leroy
@ 2021-12-08 17:18 ` Christophe Leroy
  2021-12-08 17:18 ` [PATCH v4 02/10] mm, hugetlbfs: Allow an arch to always use generic versions of get_unmapped_area functions Christophe Leroy
                   ` (8 subsequent siblings)
  9 siblings, 0 replies; 27+ messages in thread
From: Christophe Leroy @ 2021-12-08 17:18 UTC (permalink / raw)
  To: Benjamin Herrenschmidt, Paul Mackerras, Michael Ellerman, alex
  Cc: Christophe Leroy, linux-kernel, linuxppc-dev, linux-mm, akpm

Commit e7142bf5d231 ("arm64, mm: make randomization selected by
generic topdown mmap layout") introduced a default version of
arch_randomize_brk() provided when
CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT is selected.

powerpc could select CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT
but needs to provide its own arch_randomize_brk().

In order to allow that, define generic version of arch_randomize_brk()
as a __weak symbol.

Cc: Alexandre Ghiti <alex@ghiti.fr>
Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
---
 mm/util.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/mm/util.c b/mm/util.c
index 741ba32a43ac..46d1a2dd7a32 100644
--- a/mm/util.c
+++ b/mm/util.c
@@ -344,7 +344,7 @@ unsigned long randomize_stack_top(unsigned long stack_top)
 }
 
 #ifdef CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT
-unsigned long arch_randomize_brk(struct mm_struct *mm)
+unsigned long __weak arch_randomize_brk(struct mm_struct *mm)
 {
 	/* Is the current task 32bit ? */
 	if (!IS_ENABLED(CONFIG_64BIT) || is_compat_task())
-- 
2.33.1

^ permalink raw reply related	[flat|nested] 27+ messages in thread

* [PATCH v4 00/10] Convert powerpc to default topdown mmap layout
@ 2021-12-08 17:18 Christophe Leroy
  2021-12-08 17:18 ` [PATCH v4 01/10] mm: Allow arch specific arch_randomize_brk() with CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT Christophe Leroy
                   ` (9 more replies)
  0 siblings, 10 replies; 27+ messages in thread
From: Christophe Leroy @ 2021-12-08 17:18 UTC (permalink / raw)
  To: Benjamin Herrenschmidt, Paul Mackerras, Michael Ellerman, alex
  Cc: Christophe Leroy, linux-kernel, linuxppc-dev, linux-mm, akpm

Rebased on top of Nic's series "powerpc: Make hash MMU code build configurable" in today's powerpc/merge-test on github

This series converts powerpc to default topdown mmap layout.

powerpc requires its own arch_get_unmapped_area() only when
slices are needed, which is only for book3s/64. First part of
the series moves slices into book3s/64 specific directories
and cleans up other subarchitectures.

Last part converts to default topdown mmap layout.

A small modification is done to core mm to allow
powerpc to still provide its own arch_randomize_brk()

Another modification is done to core mm to allow powerpc
to use generic versions of get_unmapped_area functions for Radix
while still providing its own implementation for Hash, the
selection between Radix and Hash being doing at runtime.

Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>

Changes in v4:
- Move arch_randomize_brk() simplification out of this series
- Add a change to core mm to enable using generic implementation
while providing arch specific one at the same time.
- Reworked radix get_unmapped_area to use generic implementation
- Rebase on top of Nic's series v6

Changes in v3:
- Fixed missing <linux/elf-randomize.h> in last patch
- Added a patch to move SZ_1T out of drivers/pci/controller/pci-xgene.c

Changes in v2:
- Moved patch 4 before patch 2
- Make generic arch_randomize_brk() __weak
- Added patch 9

Christophe Leroy (10):
  mm: Allow arch specific arch_randomize_brk() with
    CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT
  mm, hugetlbfs: Allow an arch to always use generic versions of
    get_unmapped_area functions
  powerpc/mm: Move vma_mmu_pagesize()
  powerpc/mm: Make slice specific to book3s/64
  powerpc/mm: Remove CONFIG_PPC_MM_SLICES
  powerpc/mm: Use generic_get_unmapped_area() and call it from
    arch_get_unmapped_area()
  powerpc/mm: Use generic_hugetlb_get_unmapped_area()
  powerpc/mm: Move get_unmapped_area functions to slice.c
  powerpc/mm: Convert to default topdown mmap layout
  powerpc/mm: Properly randomise mmap with slices

 arch/powerpc/Kconfig                          |   2 +-
 arch/powerpc/include/asm/book3s/64/hugetlb.h  |   4 -
 arch/powerpc/include/asm/book3s/64/mmu-hash.h |   1 +
 arch/powerpc/include/asm/book3s/64/mmu.h      |   6 -
 arch/powerpc/include/asm/book3s/64/slice.h    |  24 ++
 arch/powerpc/include/asm/hugetlb.h            |   2 +-
 arch/powerpc/include/asm/paca.h               |   7 -
 arch/powerpc/include/asm/page.h               |   1 -
 arch/powerpc/include/asm/processor.h          |   2 -
 arch/powerpc/include/asm/slice.h              |  46 ----
 arch/powerpc/kernel/paca.c                    |   5 -
 arch/powerpc/mm/Makefile                      |   3 +-
 arch/powerpc/mm/book3s64/Makefile             |   2 +-
 arch/powerpc/mm/book3s64/hash_utils.c         |  14 -
 arch/powerpc/mm/book3s64/radix_hugetlbpage.c  |  55 ----
 arch/powerpc/mm/{ => book3s64}/slice.c        |  71 ++++-
 arch/powerpc/mm/hugetlbpage.c                 |  34 ---
 arch/powerpc/mm/mmap.c                        | 256 ------------------
 arch/powerpc/mm/nohash/mmu_context.c          |   9 -
 arch/powerpc/mm/nohash/tlb.c                  |   4 -
 arch/powerpc/platforms/Kconfig.cputype        |   4 -
 fs/hugetlbfs/inode.c                          |  17 +-
 include/linux/hugetlb.h                       |   5 +
 include/linux/sched/mm.h                      |   9 +
 mm/mmap.c                                     |  31 ++-
 mm/util.c                                     |   2 +-
 26 files changed, 139 insertions(+), 477 deletions(-)
 delete mode 100644 arch/powerpc/include/asm/slice.h
 rename arch/powerpc/mm/{ => book3s64}/slice.c (91%)
 delete mode 100644 arch/powerpc/mm/mmap.c

-- 
2.33.1

^ permalink raw reply	[flat|nested] 27+ messages in thread

* [PATCH v4 02/10] mm, hugetlbfs: Allow an arch to always use generic versions of get_unmapped_area functions
  2021-12-08 17:18 [PATCH v4 00/10] Convert powerpc to default topdown mmap layout Christophe Leroy
  2021-12-08 17:18 ` [PATCH v4 01/10] mm: Allow arch specific arch_randomize_brk() with CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT Christophe Leroy
@ 2021-12-08 17:18 ` Christophe Leroy
  2021-12-09  9:40   ` Nicholas Piggin
  2021-12-08 17:18 ` [PATCH v4 03/10] powerpc/mm: Move vma_mmu_pagesize() Christophe Leroy
                   ` (7 subsequent siblings)
  9 siblings, 1 reply; 27+ messages in thread
From: Christophe Leroy @ 2021-12-08 17:18 UTC (permalink / raw)
  To: Benjamin Herrenschmidt, Paul Mackerras, Michael Ellerman, alex
  Cc: Christophe Leroy, linux-kernel, linuxppc-dev, linux-mm, akpm

Unlike most architectures, powerpc can only define at runtime
if it is going to use the generic arch_get_unmapped_area() or not.

Today, powerpc has a copy of the generic arch_get_unmapped_area()
because when selection HAVE_ARCH_UNMAPPED_AREA the generic
arch_get_unmapped_area() is not available.

Rename it generic_get_unmapped_area() and make it independent of
HAVE_ARCH_UNMAPPED_AREA.

Do the same for arch_get_unmapped_area_topdown() versus
HAVE_ARCH_UNMAPPED_AREA_TOPDOWN.

Do the same for hugetlb_get_unmapped_area() versus
HAVE_ARCH_HUGETLB_UNMAPPED_AREA.

Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
---
 fs/hugetlbfs/inode.c     | 17 +++++++++++++----
 include/linux/hugetlb.h  |  5 +++++
 include/linux/sched/mm.h |  9 +++++++++
 mm/mmap.c                | 31 ++++++++++++++++++++++++-------
 4 files changed, 51 insertions(+), 11 deletions(-)

diff --git a/fs/hugetlbfs/inode.c b/fs/hugetlbfs/inode.c
index 49d2e686be74..c7cde4e5924d 100644
--- a/fs/hugetlbfs/inode.c
+++ b/fs/hugetlbfs/inode.c
@@ -195,7 +195,6 @@ static int hugetlbfs_file_mmap(struct file *file, struct vm_area_struct *vma)
  * Called under mmap_write_lock(mm).
  */
 
-#ifndef HAVE_ARCH_HUGETLB_UNMAPPED_AREA
 static unsigned long
 hugetlb_get_unmapped_area_bottomup(struct file *file, unsigned long addr,
 		unsigned long len, unsigned long pgoff, unsigned long flags)
@@ -244,9 +243,10 @@ hugetlb_get_unmapped_area_topdown(struct file *file, unsigned long addr,
 	return addr;
 }
 
-static unsigned long
-hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
-		unsigned long len, unsigned long pgoff, unsigned long flags)
+unsigned long
+generic_hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
+				  unsigned long len, unsigned long pgoff,
+				  unsigned long flags)
 {
 	struct mm_struct *mm = current->mm;
 	struct vm_area_struct *vma;
@@ -282,6 +282,15 @@ hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
 	return hugetlb_get_unmapped_area_bottomup(file, addr, len,
 			pgoff, flags);
 }
+
+#ifndef HAVE_ARCH_HUGETLB_UNMAPPED_AREA
+static unsigned long
+hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
+			  unsigned long len, unsigned long pgoff,
+			  unsigned long flags)
+{
+	return generic_hugetlb_get_unmapped_area(file, addr, len, pgoff, flags);
+}
 #endif
 
 static size_t
diff --git a/include/linux/hugetlb.h b/include/linux/hugetlb.h
index 00351ccb49a3..df899d1937ff 100644
--- a/include/linux/hugetlb.h
+++ b/include/linux/hugetlb.h
@@ -513,6 +513,11 @@ unsigned long hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
 					unsigned long flags);
 #endif /* HAVE_ARCH_HUGETLB_UNMAPPED_AREA */
 
+unsigned long
+generic_hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
+				  unsigned long len, unsigned long pgoff,
+				  unsigned long flags);
+
 /*
  * huegtlb page specific state flags.  These flags are located in page.private
  * of the hugetlb head page.  Functions created via the below macros should be
diff --git a/include/linux/sched/mm.h b/include/linux/sched/mm.h
index aca874d33fe6..2584f7c13f69 100644
--- a/include/linux/sched/mm.h
+++ b/include/linux/sched/mm.h
@@ -144,6 +144,15 @@ extern unsigned long
 arch_get_unmapped_area_topdown(struct file *filp, unsigned long addr,
 			  unsigned long len, unsigned long pgoff,
 			  unsigned long flags);
+
+unsigned long
+generic_get_unmapped_area(struct file *filp, unsigned long addr,
+			  unsigned long len, unsigned long pgoff,
+			  unsigned long flags);
+unsigned long
+generic_get_unmapped_area_topdown(struct file *filp, unsigned long addr,
+				  unsigned long len, unsigned long pgoff,
+				  unsigned long flags);
 #else
 static inline void arch_pick_mmap_layout(struct mm_struct *mm,
 					 struct rlimit *rlim_stack) {}
diff --git a/mm/mmap.c b/mm/mmap.c
index bfb0ea164a90..7ac6a07ff382 100644
--- a/mm/mmap.c
+++ b/mm/mmap.c
@@ -2131,10 +2131,10 @@ unsigned long vm_unmapped_area(struct vm_unmapped_area_info *info)
  *
  * This function "knows" that -ENOMEM has the bits set.
  */
-#ifndef HAVE_ARCH_UNMAPPED_AREA
 unsigned long
-arch_get_unmapped_area(struct file *filp, unsigned long addr,
-		unsigned long len, unsigned long pgoff, unsigned long flags)
+generic_get_unmapped_area(struct file *filp, unsigned long addr,
+			  unsigned long len, unsigned long pgoff,
+			  unsigned long flags)
 {
 	struct mm_struct *mm = current->mm;
 	struct vm_area_struct *vma, *prev;
@@ -2164,17 +2164,25 @@ arch_get_unmapped_area(struct file *filp, unsigned long addr,
 	info.align_offset = 0;
 	return vm_unmapped_area(&info);
 }
+
+#ifndef HAVE_ARCH_UNMAPPED_AREA
+unsigned long
+arch_get_unmapped_area(struct file *filp, unsigned long addr,
+		       unsigned long len, unsigned long pgoff,
+		       unsigned long flags)
+{
+	return generic_get_unmapped_area(filp, addr, len, pgoff, flags);
+}
 #endif
 
 /*
  * This mmap-allocator allocates new areas top-down from below the
  * stack's low limit (the base):
  */
-#ifndef HAVE_ARCH_UNMAPPED_AREA_TOPDOWN
 unsigned long
-arch_get_unmapped_area_topdown(struct file *filp, unsigned long addr,
-			  unsigned long len, unsigned long pgoff,
-			  unsigned long flags)
+generic_get_unmapped_area_topdown(struct file *filp, unsigned long addr,
+				  unsigned long len, unsigned long pgoff,
+				  unsigned long flags)
 {
 	struct vm_area_struct *vma, *prev;
 	struct mm_struct *mm = current->mm;
@@ -2222,6 +2230,15 @@ arch_get_unmapped_area_topdown(struct file *filp, unsigned long addr,
 
 	return addr;
 }
+
+#ifndef HAVE_ARCH_UNMAPPED_AREA_TOPDOWN
+unsigned long
+arch_get_unmapped_area_topdown(struct file *filp, unsigned long addr,
+			       unsigned long len, unsigned long pgoff,
+			       unsigned long flags)
+{
+	return generic_get_unmapped_area_topdown(filp, addr, len, pgoff, flags);
+}
 #endif
 
 unsigned long
-- 
2.33.1

^ permalink raw reply related	[flat|nested] 27+ messages in thread

* [PATCH v4 03/10] powerpc/mm: Move vma_mmu_pagesize()
  2021-12-08 17:18 [PATCH v4 00/10] Convert powerpc to default topdown mmap layout Christophe Leroy
  2021-12-08 17:18 ` [PATCH v4 01/10] mm: Allow arch specific arch_randomize_brk() with CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT Christophe Leroy
  2021-12-08 17:18 ` [PATCH v4 02/10] mm, hugetlbfs: Allow an arch to always use generic versions of get_unmapped_area functions Christophe Leroy
@ 2021-12-08 17:18 ` Christophe Leroy
  2021-12-09  9:36   ` Nicholas Piggin
  2021-12-08 17:18 ` [PATCH v4 05/10] powerpc/mm: Remove CONFIG_PPC_MM_SLICES Christophe Leroy
                   ` (6 subsequent siblings)
  9 siblings, 1 reply; 27+ messages in thread
From: Christophe Leroy @ 2021-12-08 17:18 UTC (permalink / raw)
  To: Benjamin Herrenschmidt, Paul Mackerras, Michael Ellerman, alex
  Cc: Christophe Leroy, linux-kernel, linuxppc-dev, linux-mm, akpm

vma_mmu_pagesize() is only required for slices,
otherwise there is a generic weak version doing the
exact same thing.

Move it to slice.c

Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
---
 arch/powerpc/mm/hugetlbpage.c | 11 -----------
 arch/powerpc/mm/slice.c       |  9 +++++++++
 2 files changed, 9 insertions(+), 11 deletions(-)

diff --git a/arch/powerpc/mm/hugetlbpage.c b/arch/powerpc/mm/hugetlbpage.c
index ddead41e2194..0eec3b61bd13 100644
--- a/arch/powerpc/mm/hugetlbpage.c
+++ b/arch/powerpc/mm/hugetlbpage.c
@@ -565,17 +565,6 @@ unsigned long hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
 }
 #endif
 
-unsigned long vma_mmu_pagesize(struct vm_area_struct *vma)
-{
-	/* With radix we don't use slice, so derive it from vma*/
-	if (IS_ENABLED(CONFIG_PPC_MM_SLICES) && !radix_enabled()) {
-		unsigned int psize = get_slice_psize(vma->vm_mm, vma->vm_start);
-
-		return 1UL << mmu_psize_to_shift(psize);
-	}
-	return vma_kernel_pagesize(vma);
-}
-
 bool __init arch_hugetlb_valid_size(unsigned long size)
 {
 	int shift = __ffs(size);
diff --git a/arch/powerpc/mm/slice.c b/arch/powerpc/mm/slice.c
index f42711f865f3..8a3ac062b71e 100644
--- a/arch/powerpc/mm/slice.c
+++ b/arch/powerpc/mm/slice.c
@@ -759,4 +759,13 @@ int slice_is_hugepage_only_range(struct mm_struct *mm, unsigned long addr,
 
 	return !slice_check_range_fits(mm, maskp, addr, len);
 }
+
+unsigned long vma_mmu_pagesize(struct vm_area_struct *vma)
+{
+	/* With radix we don't use slice, so derive it from vma*/
+	if (radix_enabled())
+		return vma_kernel_pagesize(vma);
+
+	return 1UL << mmu_psize_to_shift(get_slice_psize(vma->vm_mm, vma->vm_start));
+}
 #endif
-- 
2.33.1

^ permalink raw reply related	[flat|nested] 27+ messages in thread

* [PATCH v4 04/10] powerpc/mm: Make slice specific to book3s/64
  2021-12-08 17:18 [PATCH v4 00/10] Convert powerpc to default topdown mmap layout Christophe Leroy
                   ` (3 preceding siblings ...)
  2021-12-08 17:18 ` [PATCH v4 05/10] powerpc/mm: Remove CONFIG_PPC_MM_SLICES Christophe Leroy
@ 2021-12-08 17:18 ` Christophe Leroy
  2021-12-08 17:18 ` [PATCH v4 06/10] powerpc/mm: Use generic_get_unmapped_area() and call it from arch_get_unmapped_area() Christophe Leroy
                   ` (4 subsequent siblings)
  9 siblings, 0 replies; 27+ messages in thread
From: Christophe Leroy @ 2021-12-08 17:18 UTC (permalink / raw)
  To: Benjamin Herrenschmidt, Paul Mackerras, Michael Ellerman, alex
  Cc: Christophe Leroy, linux-kernel, linuxppc-dev, linux-mm, akpm,
	Nicholas Piggin

Since commit 555904d07eef ("powerpc/8xx: MM_SLICE is not needed
anymore") only book3s/64 selects CONFIG_PPC_MM_SLICES.

Move slice.c into mm/book3s64/

Move necessary stuff in asm/book3s/64/slice.h and
remove asm/slice.h

Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
Reviewed-by: Nicholas Piggin <npiggin@gmail.com>
---
 arch/powerpc/include/asm/book3s/64/mmu-hash.h |  1 +
 arch/powerpc/include/asm/book3s/64/slice.h    | 18 ++++++++
 arch/powerpc/include/asm/page.h               |  1 -
 arch/powerpc/include/asm/slice.h              | 46 -------------------
 arch/powerpc/mm/Makefile                      |  1 -
 arch/powerpc/mm/book3s64/Makefile             |  1 +
 arch/powerpc/mm/{ => book3s64}/slice.c        |  2 -
 arch/powerpc/mm/nohash/mmu_context.c          |  9 ----
 arch/powerpc/mm/nohash/tlb.c                  |  4 --
 9 files changed, 20 insertions(+), 63 deletions(-)
 delete mode 100644 arch/powerpc/include/asm/slice.h
 rename arch/powerpc/mm/{ => book3s64}/slice.c (99%)

diff --git a/arch/powerpc/include/asm/book3s/64/mmu-hash.h b/arch/powerpc/include/asm/book3s/64/mmu-hash.h
index 21f780942911..1c4eebbc69c9 100644
--- a/arch/powerpc/include/asm/book3s/64/mmu-hash.h
+++ b/arch/powerpc/include/asm/book3s/64/mmu-hash.h
@@ -18,6 +18,7 @@
  * complete pgtable.h but only a portion of it.
  */
 #include <asm/book3s/64/pgtable.h>
+#include <asm/book3s/64/slice.h>
 #include <asm/task_size_64.h>
 #include <asm/cpu_has_feature.h>
 
diff --git a/arch/powerpc/include/asm/book3s/64/slice.h b/arch/powerpc/include/asm/book3s/64/slice.h
index f0d3194ba41b..5b0f7105bc8b 100644
--- a/arch/powerpc/include/asm/book3s/64/slice.h
+++ b/arch/powerpc/include/asm/book3s/64/slice.h
@@ -2,6 +2,8 @@
 #ifndef _ASM_POWERPC_BOOK3S_64_SLICE_H
 #define _ASM_POWERPC_BOOK3S_64_SLICE_H
 
+#ifndef __ASSEMBLY__
+
 #define SLICE_LOW_SHIFT		28
 #define SLICE_LOW_TOP		(0x100000000ul)
 #define SLICE_NUM_LOW		(SLICE_LOW_TOP >> SLICE_LOW_SHIFT)
@@ -13,4 +15,20 @@
 
 #define SLB_ADDR_LIMIT_DEFAULT	DEFAULT_MAP_WINDOW_USER64
 
+struct mm_struct;
+
+unsigned long slice_get_unmapped_area(unsigned long addr, unsigned long len,
+				      unsigned long flags, unsigned int psize,
+				      int topdown);
+
+unsigned int get_slice_psize(struct mm_struct *mm, unsigned long addr);
+
+void slice_set_range_psize(struct mm_struct *mm, unsigned long start,
+			   unsigned long len, unsigned int psize);
+
+void slice_init_new_context_exec(struct mm_struct *mm);
+void slice_setup_new_exec(void);
+
+#endif /* __ASSEMBLY__ */
+
 #endif /* _ASM_POWERPC_BOOK3S_64_SLICE_H */
diff --git a/arch/powerpc/include/asm/page.h b/arch/powerpc/include/asm/page.h
index 254687258f42..62e0c6f12869 100644
--- a/arch/powerpc/include/asm/page.h
+++ b/arch/powerpc/include/asm/page.h
@@ -329,6 +329,5 @@ static inline unsigned long kaslr_offset(void)
 
 #include <asm-generic/memory_model.h>
 #endif /* __ASSEMBLY__ */
-#include <asm/slice.h>
 
 #endif /* _ASM_POWERPC_PAGE_H */
diff --git a/arch/powerpc/include/asm/slice.h b/arch/powerpc/include/asm/slice.h
deleted file mode 100644
index 0bdd9c62eca0..000000000000
--- a/arch/powerpc/include/asm/slice.h
+++ /dev/null
@@ -1,46 +0,0 @@
-/* SPDX-License-Identifier: GPL-2.0 */
-#ifndef _ASM_POWERPC_SLICE_H
-#define _ASM_POWERPC_SLICE_H
-
-#ifdef CONFIG_PPC_BOOK3S_64
-#include <asm/book3s/64/slice.h>
-#endif
-
-#ifndef __ASSEMBLY__
-
-struct mm_struct;
-
-#ifdef CONFIG_PPC_MM_SLICES
-
-#ifdef CONFIG_HUGETLB_PAGE
-#define HAVE_ARCH_HUGETLB_UNMAPPED_AREA
-#endif
-#define HAVE_ARCH_UNMAPPED_AREA
-#define HAVE_ARCH_UNMAPPED_AREA_TOPDOWN
-
-unsigned long slice_get_unmapped_area(unsigned long addr, unsigned long len,
-				      unsigned long flags, unsigned int psize,
-				      int topdown);
-
-unsigned int get_slice_psize(struct mm_struct *mm, unsigned long addr);
-
-void slice_set_range_psize(struct mm_struct *mm, unsigned long start,
-			   unsigned long len, unsigned int psize);
-
-void slice_init_new_context_exec(struct mm_struct *mm);
-void slice_setup_new_exec(void);
-
-#else /* CONFIG_PPC_MM_SLICES */
-
-static inline void slice_init_new_context_exec(struct mm_struct *mm) {}
-
-static inline unsigned int get_slice_psize(struct mm_struct *mm, unsigned long addr)
-{
-	return 0;
-}
-
-#endif /* CONFIG_PPC_MM_SLICES */
-
-#endif /* __ASSEMBLY__ */
-
-#endif /* _ASM_POWERPC_SLICE_H */
diff --git a/arch/powerpc/mm/Makefile b/arch/powerpc/mm/Makefile
index df8172da2301..d4c20484dad9 100644
--- a/arch/powerpc/mm/Makefile
+++ b/arch/powerpc/mm/Makefile
@@ -14,7 +14,6 @@ obj-$(CONFIG_PPC_MMU_NOHASH)	+= nohash/
 obj-$(CONFIG_PPC_BOOK3S_32)	+= book3s32/
 obj-$(CONFIG_PPC_BOOK3S_64)	+= book3s64/
 obj-$(CONFIG_NUMA) += numa.o
-obj-$(CONFIG_PPC_MM_SLICES)	+= slice.o
 obj-$(CONFIG_HUGETLB_PAGE)	+= hugetlbpage.o
 obj-$(CONFIG_NOT_COHERENT_CACHE) += dma-noncoherent.o
 obj-$(CONFIG_PPC_COPRO_BASE)	+= copro_fault.o
diff --git a/arch/powerpc/mm/book3s64/Makefile b/arch/powerpc/mm/book3s64/Makefile
index 2d50cac499c5..af2f3e75d458 100644
--- a/arch/powerpc/mm/book3s64/Makefile
+++ b/arch/powerpc/mm/book3s64/Makefile
@@ -21,6 +21,7 @@ obj-$(CONFIG_PPC_RADIX_MMU)	+= radix_hugetlbpage.o
 endif
 obj-$(CONFIG_SPAPR_TCE_IOMMU)	+= iommu_api.o
 obj-$(CONFIG_PPC_PKEY)	+= pkeys.o
+obj-$(CONFIG_PPC_MM_SLICES)	+= slice.o
 
 # Instrumenting the SLB fault path can lead to duplicate SLB entries
 KCOV_INSTRUMENT_slb.o := n
diff --git a/arch/powerpc/mm/slice.c b/arch/powerpc/mm/book3s64/slice.c
similarity index 99%
rename from arch/powerpc/mm/slice.c
rename to arch/powerpc/mm/book3s64/slice.c
index 8a3ac062b71e..e4382713746d 100644
--- a/arch/powerpc/mm/slice.c
+++ b/arch/powerpc/mm/book3s64/slice.c
@@ -692,7 +692,6 @@ void slice_init_new_context_exec(struct mm_struct *mm)
 		bitmap_fill(mask->high_slices, SLICE_NUM_HIGH);
 }
 
-#ifdef CONFIG_PPC_BOOK3S_64
 void slice_setup_new_exec(void)
 {
 	struct mm_struct *mm = current->mm;
@@ -704,7 +703,6 @@ void slice_setup_new_exec(void)
 
 	mm_ctx_set_slb_addr_limit(&mm->context, DEFAULT_MAP_WINDOW);
 }
-#endif
 
 void slice_set_range_psize(struct mm_struct *mm, unsigned long start,
 			   unsigned long len, unsigned int psize)
diff --git a/arch/powerpc/mm/nohash/mmu_context.c b/arch/powerpc/mm/nohash/mmu_context.c
index 85b048f04c56..ccd5819b1bd9 100644
--- a/arch/powerpc/mm/nohash/mmu_context.c
+++ b/arch/powerpc/mm/nohash/mmu_context.c
@@ -317,15 +317,6 @@ void switch_mmu_context(struct mm_struct *prev, struct mm_struct *next,
  */
 int init_new_context(struct task_struct *t, struct mm_struct *mm)
 {
-	/*
-	 * We have MMU_NO_CONTEXT set to be ~0. Hence check
-	 * explicitly against context.id == 0. This ensures that we properly
-	 * initialize context slice details for newly allocated mm's (which will
-	 * have id == 0) and don't alter context slice inherited via fork (which
-	 * will have id != 0).
-	 */
-	if (mm->context.id == 0)
-		slice_init_new_context_exec(mm);
 	mm->context.id = MMU_NO_CONTEXT;
 	mm->context.active = 0;
 	pte_frag_set(&mm->context, NULL);
diff --git a/arch/powerpc/mm/nohash/tlb.c b/arch/powerpc/mm/nohash/tlb.c
index 311281063d48..3359cf7c2a61 100644
--- a/arch/powerpc/mm/nohash/tlb.c
+++ b/arch/powerpc/mm/nohash/tlb.c
@@ -773,9 +773,5 @@ void __init early_init_mmu(void)
 #ifdef CONFIG_PPC_47x
 	early_init_mmu_47x();
 #endif
-
-#ifdef CONFIG_PPC_MM_SLICES
-	mm_ctx_set_slb_addr_limit(&init_mm.context, SLB_ADDR_LIMIT_DEFAULT);
-#endif
 }
 #endif /* CONFIG_PPC64 */
-- 
2.33.1

^ permalink raw reply related	[flat|nested] 27+ messages in thread

* [PATCH v4 05/10] powerpc/mm: Remove CONFIG_PPC_MM_SLICES
  2021-12-08 17:18 [PATCH v4 00/10] Convert powerpc to default topdown mmap layout Christophe Leroy
                   ` (2 preceding siblings ...)
  2021-12-08 17:18 ` [PATCH v4 03/10] powerpc/mm: Move vma_mmu_pagesize() Christophe Leroy
@ 2021-12-08 17:18 ` Christophe Leroy
  2021-12-08 17:18 ` [PATCH v4 04/10] powerpc/mm: Make slice specific to book3s/64 Christophe Leroy
                   ` (5 subsequent siblings)
  9 siblings, 0 replies; 27+ messages in thread
From: Christophe Leroy @ 2021-12-08 17:18 UTC (permalink / raw)
  To: Benjamin Herrenschmidt, Paul Mackerras, Michael Ellerman, alex
  Cc: Christophe Leroy, linux-kernel, linuxppc-dev, linux-mm, akpm,
	Nicholas Piggin

CONFIG_PPC_MM_SLICES is always selected by hash book3s/64.
CONFIG_PPC_MM_SLICES is never selected by other platforms.

Remove it.

Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
Reviewed-by: Nicholas Piggin <npiggin@gmail.com>
---
 arch/powerpc/include/asm/hugetlb.h     |  2 +-
 arch/powerpc/include/asm/paca.h        |  7 -------
 arch/powerpc/kernel/paca.c             |  5 -----
 arch/powerpc/mm/book3s64/Makefile      |  3 +--
 arch/powerpc/mm/book3s64/hash_utils.c  | 14 --------------
 arch/powerpc/mm/hugetlbpage.c          |  2 +-
 arch/powerpc/mm/mmap.c                 |  4 ++--
 arch/powerpc/platforms/Kconfig.cputype |  4 ----
 8 files changed, 5 insertions(+), 36 deletions(-)

diff --git a/arch/powerpc/include/asm/hugetlb.h b/arch/powerpc/include/asm/hugetlb.h
index f18c543bc01d..86a60ba6bd2a 100644
--- a/arch/powerpc/include/asm/hugetlb.h
+++ b/arch/powerpc/include/asm/hugetlb.h
@@ -24,7 +24,7 @@ static inline int is_hugepage_only_range(struct mm_struct *mm,
 					 unsigned long addr,
 					 unsigned long len)
 {
-	if (IS_ENABLED(CONFIG_PPC_MM_SLICES) && !radix_enabled())
+	if (IS_ENABLED(CONFIG_PPC_64S_HASH_MMU) && !radix_enabled())
 		return slice_is_hugepage_only_range(mm, addr, len);
 	return 0;
 }
diff --git a/arch/powerpc/include/asm/paca.h b/arch/powerpc/include/asm/paca.h
index 295573a82c66..bd4dd02e61c8 100644
--- a/arch/powerpc/include/asm/paca.h
+++ b/arch/powerpc/include/asm/paca.h
@@ -152,16 +152,9 @@ struct paca_struct {
 	struct tlb_core_data tcd;
 #endif /* CONFIG_PPC_BOOK3E */
 
-#ifdef CONFIG_PPC_BOOK3S
 #ifdef CONFIG_PPC_64S_HASH_MMU
-#ifdef CONFIG_PPC_MM_SLICES
 	unsigned char mm_ctx_low_slices_psize[BITS_PER_LONG / BITS_PER_BYTE];
 	unsigned char mm_ctx_high_slices_psize[SLICE_ARRAY_SIZE];
-#else
-	u16 mm_ctx_user_psize;
-	u16 mm_ctx_sllp;
-#endif
-#endif
 #endif
 
 	/*
diff --git a/arch/powerpc/kernel/paca.c b/arch/powerpc/kernel/paca.c
index 39da688a9455..ba593fd60124 100644
--- a/arch/powerpc/kernel/paca.c
+++ b/arch/powerpc/kernel/paca.c
@@ -344,15 +344,10 @@ void copy_mm_to_paca(struct mm_struct *mm)
 {
 	mm_context_t *context = &mm->context;
 
-#ifdef CONFIG_PPC_MM_SLICES
 	VM_BUG_ON(!mm_ctx_slb_addr_limit(context));
 	memcpy(&get_paca()->mm_ctx_low_slices_psize, mm_ctx_low_slices(context),
 	       LOW_SLICE_ARRAY_SZ);
 	memcpy(&get_paca()->mm_ctx_high_slices_psize, mm_ctx_high_slices(context),
 	       TASK_SLICE_ARRAY_SZ(context));
-#else /* CONFIG_PPC_MM_SLICES */
-	get_paca()->mm_ctx_user_psize = context->user_psize;
-	get_paca()->mm_ctx_sllp = context->sllp;
-#endif
 }
 #endif /* CONFIG_PPC_64S_HASH_MMU */
diff --git a/arch/powerpc/mm/book3s64/Makefile b/arch/powerpc/mm/book3s64/Makefile
index af2f3e75d458..d527dc8e30a8 100644
--- a/arch/powerpc/mm/book3s64/Makefile
+++ b/arch/powerpc/mm/book3s64/Makefile
@@ -5,7 +5,7 @@ ccflags-y	:= $(NO_MINIMAL_TOC)
 obj-y				+= mmu_context.o pgtable.o trace.o
 ifdef CONFIG_PPC_64S_HASH_MMU
 CFLAGS_REMOVE_slb.o = $(CC_FLAGS_FTRACE)
-obj-y				+= hash_pgtable.o hash_utils.o hash_tlb.o slb.o
+obj-y				+= hash_pgtable.o hash_utils.o hash_tlb.o slb.o slice.o
 obj-$(CONFIG_PPC_HASH_MMU_NATIVE)	+= hash_native.o
 obj-$(CONFIG_PPC_4K_PAGES)	+= hash_4k.o
 obj-$(CONFIG_PPC_64K_PAGES)	+= hash_64k.o
@@ -21,7 +21,6 @@ obj-$(CONFIG_PPC_RADIX_MMU)	+= radix_hugetlbpage.o
 endif
 obj-$(CONFIG_SPAPR_TCE_IOMMU)	+= iommu_api.o
 obj-$(CONFIG_PPC_PKEY)	+= pkeys.o
-obj-$(CONFIG_PPC_MM_SLICES)	+= slice.o
 
 # Instrumenting the SLB fault path can lead to duplicate SLB entries
 KCOV_INSTRUMENT_slb.o := n
diff --git a/arch/powerpc/mm/book3s64/hash_utils.c b/arch/powerpc/mm/book3s64/hash_utils.c
index eced266dc5e9..7ecadf5e6bf9 100644
--- a/arch/powerpc/mm/book3s64/hash_utils.c
+++ b/arch/powerpc/mm/book3s64/hash_utils.c
@@ -1264,7 +1264,6 @@ unsigned int hash_page_do_lazy_icache(unsigned int pp, pte_t pte, int trap)
 	return pp;
 }
 
-#ifdef CONFIG_PPC_MM_SLICES
 static unsigned int get_paca_psize(unsigned long addr)
 {
 	unsigned char *psizes;
@@ -1281,12 +1280,6 @@ static unsigned int get_paca_psize(unsigned long addr)
 	return (psizes[index >> 1] >> (mask_index * 4)) & 0xF;
 }
 
-#else
-unsigned int get_paca_psize(unsigned long addr)
-{
-	return get_paca()->mm_ctx_user_psize;
-}
-#endif
 
 /*
  * Demote a segment to using 4k pages.
@@ -1710,7 +1703,6 @@ DEFINE_INTERRUPT_HANDLER_RAW(do_hash_fault)
 	return 0;
 }
 
-#ifdef CONFIG_PPC_MM_SLICES
 static bool should_hash_preload(struct mm_struct *mm, unsigned long ea)
 {
 	int psize = get_slice_psize(mm, ea);
@@ -1727,12 +1719,6 @@ static bool should_hash_preload(struct mm_struct *mm, unsigned long ea)
 
 	return true;
 }
-#else
-static bool should_hash_preload(struct mm_struct *mm, unsigned long ea)
-{
-	return true;
-}
-#endif
 
 static void hash_preload(struct mm_struct *mm, pte_t *ptep, unsigned long ea,
 			 bool is_exec, unsigned long trap)
diff --git a/arch/powerpc/mm/hugetlbpage.c b/arch/powerpc/mm/hugetlbpage.c
index 0eec3b61bd13..f18b3a1d18f0 100644
--- a/arch/powerpc/mm/hugetlbpage.c
+++ b/arch/powerpc/mm/hugetlbpage.c
@@ -558,7 +558,7 @@ unsigned long hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
 		return radix__hugetlb_get_unmapped_area(file, addr, len,
 						       pgoff, flags);
 #endif
-#ifdef CONFIG_PPC_MM_SLICES
+#ifdef CONFIG_PPC_64S_HASH_MMU
 	return slice_get_unmapped_area(addr, len, flags, file_to_psize(file), 1);
 #endif
 	BUG();
diff --git a/arch/powerpc/mm/mmap.c b/arch/powerpc/mm/mmap.c
index c475cf810aa8..9b0d6e395bc0 100644
--- a/arch/powerpc/mm/mmap.c
+++ b/arch/powerpc/mm/mmap.c
@@ -190,7 +190,7 @@ unsigned long arch_get_unmapped_area(struct file *filp,
 				     unsigned long pgoff,
 				     unsigned long flags)
 {
-#ifdef CONFIG_PPC_MM_SLICES
+#ifdef CONFIG_PPC_64S_HASH_MMU
 	return slice_get_unmapped_area(addr, len, flags,
 				       mm_ctx_user_psize(&current->mm->context), 0);
 #else
@@ -204,7 +204,7 @@ unsigned long arch_get_unmapped_area_topdown(struct file *filp,
 					     const unsigned long pgoff,
 					     const unsigned long flags)
 {
-#ifdef CONFIG_PPC_MM_SLICES
+#ifdef CONFIG_PPC_64S_HASH_MMU
 	return slice_get_unmapped_area(addr0, len, flags,
 				       mm_ctx_user_psize(&current->mm->context), 1);
 #else
diff --git a/arch/powerpc/platforms/Kconfig.cputype b/arch/powerpc/platforms/Kconfig.cputype
index 87bc1929ee5a..c775b566e7b4 100644
--- a/arch/powerpc/platforms/Kconfig.cputype
+++ b/arch/powerpc/platforms/Kconfig.cputype
@@ -376,7 +376,6 @@ config SPE
 config PPC_64S_HASH_MMU
 	bool "Hash MMU Support"
 	depends on PPC_BOOK3S_64
-	select PPC_MM_SLICES
 	default y
 	help
 	  Enable support for the Power ISA Hash style MMU. This is implemented
@@ -450,9 +449,6 @@ config PPC_BOOK3E_MMU
 	def_bool y
 	depends on FSL_BOOKE || PPC_BOOK3E
 
-config PPC_MM_SLICES
-	bool
-
 config PPC_HAVE_PMU_SUPPORT
 	bool
 
-- 
2.33.1

^ permalink raw reply related	[flat|nested] 27+ messages in thread

* [PATCH v4 06/10] powerpc/mm: Use generic_get_unmapped_area() and call it from arch_get_unmapped_area()
  2021-12-08 17:18 [PATCH v4 00/10] Convert powerpc to default topdown mmap layout Christophe Leroy
                   ` (4 preceding siblings ...)
  2021-12-08 17:18 ` [PATCH v4 04/10] powerpc/mm: Make slice specific to book3s/64 Christophe Leroy
@ 2021-12-08 17:18 ` Christophe Leroy
  2021-12-09  9:50   ` Nicholas Piggin
  2021-12-13 13:02   ` Michael Ellerman
  2021-12-08 17:18 ` [PATCH v4 08/10] powerpc/mm: Move get_unmapped_area functions to slice.c Christophe Leroy
                   ` (3 subsequent siblings)
  9 siblings, 2 replies; 27+ messages in thread
From: Christophe Leroy @ 2021-12-08 17:18 UTC (permalink / raw)
  To: Benjamin Herrenschmidt, Paul Mackerras, Michael Ellerman, alex
  Cc: Christophe Leroy, linux-kernel, linuxppc-dev, linux-mm, akpm

Use the generic version of arch_get_unmapped_area() which
is now available at all time instead of its copy
radix__arch_get_unmapped_area()

Instead of setting mm->get_unmapped_area() to either
arch_get_unmapped_area() or generic_get_unmapped_area(),
always set it to arch_get_unmapped_area() and call
generic_get_unmapped_area() from there when radix is enabled.

Do the same with radix__arch_get_unmapped_area_topdown()

Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
---
 arch/powerpc/mm/mmap.c | 127 ++---------------------------------------
 1 file changed, 6 insertions(+), 121 deletions(-)

diff --git a/arch/powerpc/mm/mmap.c b/arch/powerpc/mm/mmap.c
index 9b0d6e395bc0..46781d0103d1 100644
--- a/arch/powerpc/mm/mmap.c
+++ b/arch/powerpc/mm/mmap.c
@@ -81,115 +81,15 @@ static inline unsigned long mmap_base(unsigned long rnd,
 }
 
 #ifdef HAVE_ARCH_UNMAPPED_AREA
-#ifdef CONFIG_PPC_RADIX_MMU
-/*
- * Same function as generic code used only for radix, because we don't need to overload
- * the generic one. But we will have to duplicate, because hash select
- * HAVE_ARCH_UNMAPPED_AREA
- */
-static unsigned long
-radix__arch_get_unmapped_area(struct file *filp, unsigned long addr,
-			     unsigned long len, unsigned long pgoff,
-			     unsigned long flags)
-{
-	struct mm_struct *mm = current->mm;
-	struct vm_area_struct *vma;
-	int fixed = (flags & MAP_FIXED);
-	unsigned long high_limit;
-	struct vm_unmapped_area_info info;
-
-	high_limit = DEFAULT_MAP_WINDOW;
-	if (addr >= high_limit || (fixed && (addr + len > high_limit)))
-		high_limit = TASK_SIZE;
-
-	if (len > high_limit)
-		return -ENOMEM;
-
-	if (fixed) {
-		if (addr > high_limit - len)
-			return -ENOMEM;
-		return addr;
-	}
-
-	if (addr) {
-		addr = PAGE_ALIGN(addr);
-		vma = find_vma(mm, addr);
-		if (high_limit - len >= addr && addr >= mmap_min_addr &&
-		    (!vma || addr + len <= vm_start_gap(vma)))
-			return addr;
-	}
-
-	info.flags = 0;
-	info.length = len;
-	info.low_limit = mm->mmap_base;
-	info.high_limit = high_limit;
-	info.align_mask = 0;
-
-	return vm_unmapped_area(&info);
-}
-
-static unsigned long
-radix__arch_get_unmapped_area_topdown(struct file *filp,
-				     const unsigned long addr0,
-				     const unsigned long len,
-				     const unsigned long pgoff,
-				     const unsigned long flags)
-{
-	struct vm_area_struct *vma;
-	struct mm_struct *mm = current->mm;
-	unsigned long addr = addr0;
-	int fixed = (flags & MAP_FIXED);
-	unsigned long high_limit;
-	struct vm_unmapped_area_info info;
-
-	high_limit = DEFAULT_MAP_WINDOW;
-	if (addr >= high_limit || (fixed && (addr + len > high_limit)))
-		high_limit = TASK_SIZE;
-
-	if (len > high_limit)
-		return -ENOMEM;
-
-	if (fixed) {
-		if (addr > high_limit - len)
-			return -ENOMEM;
-		return addr;
-	}
-
-	if (addr) {
-		addr = PAGE_ALIGN(addr);
-		vma = find_vma(mm, addr);
-		if (high_limit - len >= addr && addr >= mmap_min_addr &&
-		    (!vma || addr + len <= vm_start_gap(vma)))
-			return addr;
-	}
-
-	info.flags = VM_UNMAPPED_AREA_TOPDOWN;
-	info.length = len;
-	info.low_limit = max(PAGE_SIZE, mmap_min_addr);
-	info.high_limit = mm->mmap_base + (high_limit - DEFAULT_MAP_WINDOW);
-	info.align_mask = 0;
-
-	addr = vm_unmapped_area(&info);
-	if (!(addr & ~PAGE_MASK))
-		return addr;
-	VM_BUG_ON(addr != -ENOMEM);
-
-	/*
-	 * A failed mmap() very likely causes application failure,
-	 * so fall back to the bottom-up function here. This scenario
-	 * can happen with large stack limits and large mmap()
-	 * allocations.
-	 */
-	return radix__arch_get_unmapped_area(filp, addr0, len, pgoff, flags);
-}
-#endif
-
 unsigned long arch_get_unmapped_area(struct file *filp,
 				     unsigned long addr,
 				     unsigned long len,
 				     unsigned long pgoff,
 				     unsigned long flags)
 {
+	if (radix_enabled())
+		return generic_get_unmapped_area(filp, addr, len, pgoff, flags);
+
 #ifdef CONFIG_PPC_64S_HASH_MMU
 	return slice_get_unmapped_area(addr, len, flags,
 				       mm_ctx_user_psize(&current->mm->context), 0);
@@ -204,6 +104,9 @@ unsigned long arch_get_unmapped_area_topdown(struct file *filp,
 					     const unsigned long pgoff,
 					     const unsigned long flags)
 {
+	if (radix_enabled())
+		return generic_get_unmapped_area_topdown(filp, addr0, len, pgoff, flags);
+
 #ifdef CONFIG_PPC_64S_HASH_MMU
 	return slice_get_unmapped_area(addr0, len, flags,
 				       mm_ctx_user_psize(&current->mm->context), 1);
@@ -213,21 +116,6 @@ unsigned long arch_get_unmapped_area_topdown(struct file *filp,
 }
 #endif /* HAVE_ARCH_UNMAPPED_AREA */
 
-static void radix__arch_pick_mmap_layout(struct mm_struct *mm,
-					unsigned long random_factor,
-					struct rlimit *rlim_stack)
-{
-#ifdef CONFIG_PPC_RADIX_MMU
-	if (mmap_is_legacy(rlim_stack)) {
-		mm->mmap_base = TASK_UNMAPPED_BASE;
-		mm->get_unmapped_area = radix__arch_get_unmapped_area;
-	} else {
-		mm->mmap_base = mmap_base(random_factor, rlim_stack);
-		mm->get_unmapped_area = radix__arch_get_unmapped_area_topdown;
-	}
-#endif
-}
-
 /*
  * This function, called very early during the creation of a new
  * process VM image, sets up which VM layout function to use:
@@ -239,9 +127,6 @@ void arch_pick_mmap_layout(struct mm_struct *mm, struct rlimit *rlim_stack)
 	if (current->flags & PF_RANDOMIZE)
 		random_factor = arch_mmap_rnd();
 
-	if (radix_enabled())
-		return radix__arch_pick_mmap_layout(mm, random_factor,
-						    rlim_stack);
 	/*
 	 * Fall back to the standard layout if the personality
 	 * bit is set, or if the expected stack growth is unlimited:
-- 
2.33.1

^ permalink raw reply related	[flat|nested] 27+ messages in thread

* [PATCH v4 07/10] powerpc/mm: Use generic_hugetlb_get_unmapped_area()
  2021-12-08 17:18 [PATCH v4 00/10] Convert powerpc to default topdown mmap layout Christophe Leroy
                   ` (6 preceding siblings ...)
  2021-12-08 17:18 ` [PATCH v4 08/10] powerpc/mm: Move get_unmapped_area functions to slice.c Christophe Leroy
@ 2021-12-08 17:18 ` Christophe Leroy
  2021-12-09 10:02   ` Nicholas Piggin
  2021-12-08 17:18 ` [PATCH v4 09/10] powerpc/mm: Convert to default topdown mmap layout Christophe Leroy
  2021-12-08 17:18 ` [PATCH v4 10/10] powerpc/mm: Properly randomise mmap with slices Christophe Leroy
  9 siblings, 1 reply; 27+ messages in thread
From: Christophe Leroy @ 2021-12-08 17:18 UTC (permalink / raw)
  To: Benjamin Herrenschmidt, Paul Mackerras, Michael Ellerman, alex
  Cc: Christophe Leroy, linux-kernel, linuxppc-dev, linux-mm, akpm

Use the generic version of arch_hugetlb_get_unmapped_area()
which is now available at all time.

Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
---
 arch/powerpc/include/asm/book3s/64/hugetlb.h |  4 --
 arch/powerpc/mm/book3s64/radix_hugetlbpage.c | 55 --------------------
 arch/powerpc/mm/hugetlbpage.c                |  4 +-
 3 files changed, 1 insertion(+), 62 deletions(-)

diff --git a/arch/powerpc/include/asm/book3s/64/hugetlb.h b/arch/powerpc/include/asm/book3s/64/hugetlb.h
index 12e150e615b7..b37a28f62cf6 100644
--- a/arch/powerpc/include/asm/book3s/64/hugetlb.h
+++ b/arch/powerpc/include/asm/book3s/64/hugetlb.h
@@ -8,10 +8,6 @@
  */
 void radix__flush_hugetlb_page(struct vm_area_struct *vma, unsigned long vmaddr);
 void radix__local_flush_hugetlb_page(struct vm_area_struct *vma, unsigned long vmaddr);
-extern unsigned long
-radix__hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
-				unsigned long len, unsigned long pgoff,
-				unsigned long flags);
 
 extern void radix__huge_ptep_modify_prot_commit(struct vm_area_struct *vma,
 						unsigned long addr, pte_t *ptep,
diff --git a/arch/powerpc/mm/book3s64/radix_hugetlbpage.c b/arch/powerpc/mm/book3s64/radix_hugetlbpage.c
index 23d3e08911d3..d2fb776febb4 100644
--- a/arch/powerpc/mm/book3s64/radix_hugetlbpage.c
+++ b/arch/powerpc/mm/book3s64/radix_hugetlbpage.c
@@ -41,61 +41,6 @@ void radix__flush_hugetlb_tlb_range(struct vm_area_struct *vma, unsigned long st
 		radix__flush_tlb_range_psize(vma->vm_mm, start, end, psize);
 }
 
-/*
- * A vairant of hugetlb_get_unmapped_area doing topdown search
- * FIXME!! should we do as x86 does or non hugetlb area does ?
- * ie, use topdown or not based on mmap_is_legacy check ?
- */
-unsigned long
-radix__hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
-				unsigned long len, unsigned long pgoff,
-				unsigned long flags)
-{
-	struct mm_struct *mm = current->mm;
-	struct vm_area_struct *vma;
-	struct hstate *h = hstate_file(file);
-	int fixed = (flags & MAP_FIXED);
-	unsigned long high_limit;
-	struct vm_unmapped_area_info info;
-
-	high_limit = DEFAULT_MAP_WINDOW;
-	if (addr >= high_limit || (fixed && (addr + len > high_limit)))
-		high_limit = TASK_SIZE;
-
-	if (len & ~huge_page_mask(h))
-		return -EINVAL;
-	if (len > high_limit)
-		return -ENOMEM;
-
-	if (fixed) {
-		if (addr > high_limit - len)
-			return -ENOMEM;
-		if (prepare_hugepage_range(file, addr, len))
-			return -EINVAL;
-		return addr;
-	}
-
-	if (addr) {
-		addr = ALIGN(addr, huge_page_size(h));
-		vma = find_vma(mm, addr);
-		if (high_limit - len >= addr && addr >= mmap_min_addr &&
-		    (!vma || addr + len <= vm_start_gap(vma)))
-			return addr;
-	}
-	/*
-	 * We are always doing an topdown search here. Slice code
-	 * does that too.
-	 */
-	info.flags = VM_UNMAPPED_AREA_TOPDOWN;
-	info.length = len;
-	info.low_limit = max(PAGE_SIZE, mmap_min_addr);
-	info.high_limit = mm->mmap_base + (high_limit - DEFAULT_MAP_WINDOW);
-	info.align_mask = PAGE_MASK & ~huge_page_mask(h);
-	info.align_offset = 0;
-
-	return vm_unmapped_area(&info);
-}
-
 void radix__huge_ptep_modify_prot_commit(struct vm_area_struct *vma,
 					 unsigned long addr, pte_t *ptep,
 					 pte_t old_pte, pte_t pte)
diff --git a/arch/powerpc/mm/hugetlbpage.c b/arch/powerpc/mm/hugetlbpage.c
index f18b3a1d18f0..bfd7f4af1e58 100644
--- a/arch/powerpc/mm/hugetlbpage.c
+++ b/arch/powerpc/mm/hugetlbpage.c
@@ -553,11 +553,9 @@ unsigned long hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
 					unsigned long len, unsigned long pgoff,
 					unsigned long flags)
 {
-#ifdef CONFIG_PPC_RADIX_MMU
 	if (radix_enabled())
-		return radix__hugetlb_get_unmapped_area(file, addr, len,
+		return generic_hugetlb_get_unmapped_area(file, addr, len,
 						       pgoff, flags);
-#endif
 #ifdef CONFIG_PPC_64S_HASH_MMU
 	return slice_get_unmapped_area(addr, len, flags, file_to_psize(file), 1);
 #endif
-- 
2.33.1

^ permalink raw reply related	[flat|nested] 27+ messages in thread

* [PATCH v4 08/10] powerpc/mm: Move get_unmapped_area functions to slice.c
  2021-12-08 17:18 [PATCH v4 00/10] Convert powerpc to default topdown mmap layout Christophe Leroy
                   ` (5 preceding siblings ...)
  2021-12-08 17:18 ` [PATCH v4 06/10] powerpc/mm: Use generic_get_unmapped_area() and call it from arch_get_unmapped_area() Christophe Leroy
@ 2021-12-08 17:18 ` Christophe Leroy
  2021-12-08 17:18 ` [PATCH v4 07/10] powerpc/mm: Use generic_hugetlb_get_unmapped_area() Christophe Leroy
                   ` (2 subsequent siblings)
  9 siblings, 0 replies; 27+ messages in thread
From: Christophe Leroy @ 2021-12-08 17:18 UTC (permalink / raw)
  To: Benjamin Herrenschmidt, Paul Mackerras, Michael Ellerman, alex
  Cc: Christophe Leroy, linux-kernel, linuxppc-dev, linux-mm, akpm

hugetlb_get_unmapped_area() is now identical to the
generic version if only RADIX is enabled, so move it
to slice.c and let it fallback on the generic one
when HASH MMU is not compiled in.

Do the same with arch_get_unmapped_area() and
arch_get_unmapped_area_topdown().

Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
---
 arch/powerpc/include/asm/book3s/64/mmu.h   |  6 ----
 arch/powerpc/include/asm/book3s/64/slice.h |  6 ++++
 arch/powerpc/mm/book3s64/slice.c           | 42 ++++++++++++++++++++++
 arch/powerpc/mm/hugetlbpage.c              | 21 -----------
 arch/powerpc/mm/mmap.c                     | 36 -------------------
 5 files changed, 48 insertions(+), 63 deletions(-)

diff --git a/arch/powerpc/include/asm/book3s/64/mmu.h b/arch/powerpc/include/asm/book3s/64/mmu.h
index 7fee46e50377..310ca3597d58 100644
--- a/arch/powerpc/include/asm/book3s/64/mmu.h
+++ b/arch/powerpc/include/asm/book3s/64/mmu.h
@@ -4,12 +4,6 @@
 
 #include <asm/page.h>
 
-#ifdef CONFIG_HUGETLB_PAGE
-#define HAVE_ARCH_HUGETLB_UNMAPPED_AREA
-#endif
-#define HAVE_ARCH_UNMAPPED_AREA
-#define HAVE_ARCH_UNMAPPED_AREA_TOPDOWN
-
 #ifndef __ASSEMBLY__
 /*
  * Page size definition
diff --git a/arch/powerpc/include/asm/book3s/64/slice.h b/arch/powerpc/include/asm/book3s/64/slice.h
index 5b0f7105bc8b..b8eb4ad271b9 100644
--- a/arch/powerpc/include/asm/book3s/64/slice.h
+++ b/arch/powerpc/include/asm/book3s/64/slice.h
@@ -4,6 +4,12 @@
 
 #ifndef __ASSEMBLY__
 
+#ifdef CONFIG_HUGETLB_PAGE
+#define HAVE_ARCH_HUGETLB_UNMAPPED_AREA
+#endif
+#define HAVE_ARCH_UNMAPPED_AREA
+#define HAVE_ARCH_UNMAPPED_AREA_TOPDOWN
+
 #define SLICE_LOW_SHIFT		28
 #define SLICE_LOW_TOP		(0x100000000ul)
 #define SLICE_NUM_LOW		(SLICE_LOW_TOP >> SLICE_LOW_SHIFT)
diff --git a/arch/powerpc/mm/book3s64/slice.c b/arch/powerpc/mm/book3s64/slice.c
index e4382713746d..03681042b807 100644
--- a/arch/powerpc/mm/book3s64/slice.c
+++ b/arch/powerpc/mm/book3s64/slice.c
@@ -639,6 +639,32 @@ unsigned long slice_get_unmapped_area(unsigned long addr, unsigned long len,
 }
 EXPORT_SYMBOL_GPL(slice_get_unmapped_area);
 
+unsigned long arch_get_unmapped_area(struct file *filp,
+				     unsigned long addr,
+				     unsigned long len,
+				     unsigned long pgoff,
+				     unsigned long flags)
+{
+	if (radix_enabled())
+		return generic_get_unmapped_area(filp, addr, len, pgoff, flags);
+
+	return slice_get_unmapped_area(addr, len, flags,
+				       mm_ctx_user_psize(&current->mm->context), 0);
+}
+
+unsigned long arch_get_unmapped_area_topdown(struct file *filp,
+					     const unsigned long addr0,
+					     const unsigned long len,
+					     const unsigned long pgoff,
+					     const unsigned long flags)
+{
+	if (radix_enabled())
+		return generic_get_unmapped_area_topdown(filp, addr0, len, pgoff, flags);
+
+	return slice_get_unmapped_area(addr0, len, flags,
+				       mm_ctx_user_psize(&current->mm->context), 1);
+}
+
 unsigned int notrace get_slice_psize(struct mm_struct *mm, unsigned long addr)
 {
 	unsigned char *psizes;
@@ -766,4 +792,20 @@ unsigned long vma_mmu_pagesize(struct vm_area_struct *vma)
 
 	return 1UL << mmu_psize_to_shift(get_slice_psize(vma->vm_mm, vma->vm_start));
 }
+
+static int file_to_psize(struct file *file)
+{
+	struct hstate *hstate = hstate_file(file);
+	return shift_to_mmu_psize(huge_page_shift(hstate));
+}
+
+unsigned long hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
+					unsigned long len, unsigned long pgoff,
+					unsigned long flags)
+{
+	if (radix_enabled())
+		return generic_hugetlb_get_unmapped_area(file, addr, len, pgoff, flags);
+
+	return slice_get_unmapped_area(addr, len, flags, file_to_psize(file), 1);
+}
 #endif
diff --git a/arch/powerpc/mm/hugetlbpage.c b/arch/powerpc/mm/hugetlbpage.c
index bfd7f4af1e58..eb9de09e49a3 100644
--- a/arch/powerpc/mm/hugetlbpage.c
+++ b/arch/powerpc/mm/hugetlbpage.c
@@ -542,27 +542,6 @@ struct page *follow_huge_pd(struct vm_area_struct *vma,
 	return page;
 }
 
-#ifdef HAVE_ARCH_HUGETLB_UNMAPPED_AREA
-static inline int file_to_psize(struct file *file)
-{
-	struct hstate *hstate = hstate_file(file);
-	return shift_to_mmu_psize(huge_page_shift(hstate));
-}
-
-unsigned long hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
-					unsigned long len, unsigned long pgoff,
-					unsigned long flags)
-{
-	if (radix_enabled())
-		return generic_hugetlb_get_unmapped_area(file, addr, len,
-						       pgoff, flags);
-#ifdef CONFIG_PPC_64S_HASH_MMU
-	return slice_get_unmapped_area(addr, len, flags, file_to_psize(file), 1);
-#endif
-	BUG();
-}
-#endif
-
 bool __init arch_hugetlb_valid_size(unsigned long size)
 {
 	int shift = __ffs(size);
diff --git a/arch/powerpc/mm/mmap.c b/arch/powerpc/mm/mmap.c
index 46781d0103d1..5972d619d274 100644
--- a/arch/powerpc/mm/mmap.c
+++ b/arch/powerpc/mm/mmap.c
@@ -80,42 +80,6 @@ static inline unsigned long mmap_base(unsigned long rnd,
 	return PAGE_ALIGN(DEFAULT_MAP_WINDOW - gap - rnd);
 }
 
-#ifdef HAVE_ARCH_UNMAPPED_AREA
-unsigned long arch_get_unmapped_area(struct file *filp,
-				     unsigned long addr,
-				     unsigned long len,
-				     unsigned long pgoff,
-				     unsigned long flags)
-{
-	if (radix_enabled())
-		return generic_get_unmapped_area(filp, addr, len, pgoff, flags);
-
-#ifdef CONFIG_PPC_64S_HASH_MMU
-	return slice_get_unmapped_area(addr, len, flags,
-				       mm_ctx_user_psize(&current->mm->context), 0);
-#else
-	BUG();
-#endif
-}
-
-unsigned long arch_get_unmapped_area_topdown(struct file *filp,
-					     const unsigned long addr0,
-					     const unsigned long len,
-					     const unsigned long pgoff,
-					     const unsigned long flags)
-{
-	if (radix_enabled())
-		return generic_get_unmapped_area_topdown(filp, addr0, len, pgoff, flags);
-
-#ifdef CONFIG_PPC_64S_HASH_MMU
-	return slice_get_unmapped_area(addr0, len, flags,
-				       mm_ctx_user_psize(&current->mm->context), 1);
-#else
-	BUG();
-#endif
-}
-#endif /* HAVE_ARCH_UNMAPPED_AREA */
-
 /*
  * This function, called very early during the creation of a new
  * process VM image, sets up which VM layout function to use:
-- 
2.33.1

^ permalink raw reply related	[flat|nested] 27+ messages in thread

* [PATCH v4 09/10] powerpc/mm: Convert to default topdown mmap layout
  2021-12-08 17:18 [PATCH v4 00/10] Convert powerpc to default topdown mmap layout Christophe Leroy
                   ` (7 preceding siblings ...)
  2021-12-08 17:18 ` [PATCH v4 07/10] powerpc/mm: Use generic_hugetlb_get_unmapped_area() Christophe Leroy
@ 2021-12-08 17:18 ` Christophe Leroy
  2021-12-09 10:15   ` Nicholas Piggin
  2021-12-08 17:18 ` [PATCH v4 10/10] powerpc/mm: Properly randomise mmap with slices Christophe Leroy
  9 siblings, 1 reply; 27+ messages in thread
From: Christophe Leroy @ 2021-12-08 17:18 UTC (permalink / raw)
  To: Benjamin Herrenschmidt, Paul Mackerras, Michael Ellerman, alex
  Cc: Christophe Leroy, linux-kernel, linuxppc-dev, linux-mm, akpm

Select CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT and
remove arch/powerpc/mm/mmap.c

This change provides standard randomisation of mmaps.

See commit 8b8addf891de ("x86/mm/32: Enable full randomization on i386
and X86_32") for all the benefits of mmap randomisation.

Comparison between powerpc implementation and the generic one:
- mmap_is_legacy() is identical.
- arch_mmap_rnd() does exactly the same allthough it's written
slightly differently.
- MIN_GAP and MAX_GAP are identical.
- mmap_base() does the same but uses STACK_RND_MASK which provides
the same values as stack_maxrandom_size().
- arch_pick_mmap_layout() is almost identical. The only difference
is that it also adds the random factor to mm->mmap_base in legacy mode.

That last point is what provides the standard randomisation of mmaps.

Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
---
 arch/powerpc/Kconfig                 |   2 +-
 arch/powerpc/include/asm/processor.h |   2 -
 arch/powerpc/mm/Makefile             |   2 +-
 arch/powerpc/mm/mmap.c               | 105 ---------------------------
 4 files changed, 2 insertions(+), 109 deletions(-)
 delete mode 100644 arch/powerpc/mm/mmap.c

diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig
index 0631c9241af3..b4ae3d8bde46 100644
--- a/arch/powerpc/Kconfig
+++ b/arch/powerpc/Kconfig
@@ -122,7 +122,6 @@ config PPC
 	select ARCH_HAS_DEBUG_WX		if STRICT_KERNEL_RWX
 	select ARCH_HAS_DEVMEM_IS_ALLOWED
 	select ARCH_HAS_DMA_MAP_DIRECT 		if PPC_PSERIES
-	select ARCH_HAS_ELF_RANDOMIZE
 	select ARCH_HAS_FORTIFY_SOURCE
 	select ARCH_HAS_GCOV_PROFILE_ALL
 	select ARCH_HAS_HUGEPD			if HUGETLB_PAGE
@@ -158,6 +157,7 @@ config PPC
 	select ARCH_USE_MEMTEST
 	select ARCH_USE_QUEUED_RWLOCKS		if PPC_QUEUED_SPINLOCKS
 	select ARCH_USE_QUEUED_SPINLOCKS	if PPC_QUEUED_SPINLOCKS
+	select ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT
 	select ARCH_WANT_IPC_PARSE_VERSION
 	select ARCH_WANT_IRQS_OFF_ACTIVATE_MM
 	select ARCH_WANT_LD_ORPHAN_WARN
diff --git a/arch/powerpc/include/asm/processor.h b/arch/powerpc/include/asm/processor.h
index 2c8686d9e964..873adaab20c8 100644
--- a/arch/powerpc/include/asm/processor.h
+++ b/arch/powerpc/include/asm/processor.h
@@ -392,8 +392,6 @@ static inline void prefetchw(const void *x)
 
 #define spin_lock_prefetch(x)	prefetchw(x)
 
-#define HAVE_ARCH_PICK_MMAP_LAYOUT
-
 /* asm stubs */
 extern unsigned long isa300_idle_stop_noloss(unsigned long psscr_val);
 extern unsigned long isa300_idle_stop_mayloss(unsigned long psscr_val);
diff --git a/arch/powerpc/mm/Makefile b/arch/powerpc/mm/Makefile
index d4c20484dad9..503a6e249940 100644
--- a/arch/powerpc/mm/Makefile
+++ b/arch/powerpc/mm/Makefile
@@ -5,7 +5,7 @@
 
 ccflags-$(CONFIG_PPC64)	:= $(NO_MINIMAL_TOC)
 
-obj-y				:= fault.o mem.o pgtable.o mmap.o maccess.o pageattr.o \
+obj-y				:= fault.o mem.o pgtable.o maccess.o pageattr.o \
 				   init_$(BITS).o pgtable_$(BITS).o \
 				   pgtable-frag.o ioremap.o ioremap_$(BITS).o \
 				   init-common.o mmu_context.o drmem.o \
diff --git a/arch/powerpc/mm/mmap.c b/arch/powerpc/mm/mmap.c
deleted file mode 100644
index 5972d619d274..000000000000
--- a/arch/powerpc/mm/mmap.c
+++ /dev/null
@@ -1,105 +0,0 @@
-// SPDX-License-Identifier: GPL-2.0-or-later
-/*
- *  flexible mmap layout support
- *
- * Copyright 2003-2004 Red Hat Inc., Durham, North Carolina.
- * All Rights Reserved.
- *
- * Started by Ingo Molnar <mingo@elte.hu>
- */
-
-#include <linux/personality.h>
-#include <linux/mm.h>
-#include <linux/random.h>
-#include <linux/sched/signal.h>
-#include <linux/sched/mm.h>
-#include <linux/elf-randomize.h>
-#include <linux/security.h>
-#include <linux/mman.h>
-
-/*
- * Top of mmap area (just below the process stack).
- *
- * Leave at least a ~128 MB hole.
- */
-#define MIN_GAP (128*1024*1024)
-#define MAX_GAP (TASK_SIZE/6*5)
-
-static inline int mmap_is_legacy(struct rlimit *rlim_stack)
-{
-	if (current->personality & ADDR_COMPAT_LAYOUT)
-		return 1;
-
-	if (rlim_stack->rlim_cur == RLIM_INFINITY)
-		return 1;
-
-	return sysctl_legacy_va_layout;
-}
-
-unsigned long arch_mmap_rnd(void)
-{
-	unsigned long shift, rnd;
-
-	shift = mmap_rnd_bits;
-#ifdef CONFIG_COMPAT
-	if (is_32bit_task())
-		shift = mmap_rnd_compat_bits;
-#endif
-	rnd = get_random_long() % (1ul << shift);
-
-	return rnd << PAGE_SHIFT;
-}
-
-static inline unsigned long stack_maxrandom_size(void)
-{
-	if (!(current->flags & PF_RANDOMIZE))
-		return 0;
-
-	/* 8MB for 32bit, 1GB for 64bit */
-	if (is_32bit_task())
-		return (1<<23);
-	else
-		return (1<<30);
-}
-
-static inline unsigned long mmap_base(unsigned long rnd,
-				      struct rlimit *rlim_stack)
-{
-	unsigned long gap = rlim_stack->rlim_cur;
-	unsigned long pad = stack_maxrandom_size() + stack_guard_gap;
-
-	/* Values close to RLIM_INFINITY can overflow. */
-	if (gap + pad > gap)
-		gap += pad;
-
-	if (gap < MIN_GAP)
-		gap = MIN_GAP;
-	else if (gap > MAX_GAP)
-		gap = MAX_GAP;
-
-	return PAGE_ALIGN(DEFAULT_MAP_WINDOW - gap - rnd);
-}
-
-/*
- * This function, called very early during the creation of a new
- * process VM image, sets up which VM layout function to use:
- */
-void arch_pick_mmap_layout(struct mm_struct *mm, struct rlimit *rlim_stack)
-{
-	unsigned long random_factor = 0UL;
-
-	if (current->flags & PF_RANDOMIZE)
-		random_factor = arch_mmap_rnd();
-
-	/*
-	 * Fall back to the standard layout if the personality
-	 * bit is set, or if the expected stack growth is unlimited:
-	 */
-	if (mmap_is_legacy(rlim_stack)) {
-		mm->mmap_base = TASK_UNMAPPED_BASE;
-		mm->get_unmapped_area = arch_get_unmapped_area;
-	} else {
-		mm->mmap_base = mmap_base(random_factor, rlim_stack);
-		mm->get_unmapped_area = arch_get_unmapped_area_topdown;
-	}
-}
-- 
2.33.1

^ permalink raw reply related	[flat|nested] 27+ messages in thread

* [PATCH v4 10/10] powerpc/mm: Properly randomise mmap with slices
  2021-12-08 17:18 [PATCH v4 00/10] Convert powerpc to default topdown mmap layout Christophe Leroy
                   ` (8 preceding siblings ...)
  2021-12-08 17:18 ` [PATCH v4 09/10] powerpc/mm: Convert to default topdown mmap layout Christophe Leroy
@ 2021-12-08 17:18 ` Christophe Leroy
  9 siblings, 0 replies; 27+ messages in thread
From: Christophe Leroy @ 2021-12-08 17:18 UTC (permalink / raw)
  To: Benjamin Herrenschmidt, Paul Mackerras, Michael Ellerman, alex
  Cc: Christophe Leroy, linux-kernel, linuxppc-dev, linux-mm, akpm

Now that powerpc switched to default topdown mmap layout,
mm->mmap_base is properly randomised.  However
slice_find_area_bottomup() doesn't use mm->mmap_base but
uses the fixed TASK_UNMAPPED_BASE instead.

slice_find_area_bottomup() being used as a fallback to
slice_find_area_topdown(), it can't use mm->mmap_base
directly.

Instead of always using TASK_UNMAPPED_BASE as base address, leave
it to the caller. When called from slice_find_area_topdown()
TASK_UNMAPPED_BASE is used. Otherwise mm->mmap_base is used.

Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
---
 arch/powerpc/mm/book3s64/slice.c | 18 +++++++-----------
 1 file changed, 7 insertions(+), 11 deletions(-)

diff --git a/arch/powerpc/mm/book3s64/slice.c b/arch/powerpc/mm/book3s64/slice.c
index 03681042b807..c0b58afb9a47 100644
--- a/arch/powerpc/mm/book3s64/slice.c
+++ b/arch/powerpc/mm/book3s64/slice.c
@@ -276,20 +276,18 @@ static bool slice_scan_available(unsigned long addr,
 }
 
 static unsigned long slice_find_area_bottomup(struct mm_struct *mm,
-					      unsigned long len,
+					      unsigned long addr, unsigned long len,
 					      const struct slice_mask *available,
 					      int psize, unsigned long high_limit)
 {
 	int pshift = max_t(int, mmu_psize_defs[psize].shift, PAGE_SHIFT);
-	unsigned long addr, found, next_end;
+	unsigned long found, next_end;
 	struct vm_unmapped_area_info info;
 
 	info.flags = 0;
 	info.length = len;
 	info.align_mask = PAGE_MASK & ((1ul << pshift) - 1);
 	info.align_offset = 0;
-
-	addr = TASK_UNMAPPED_BASE;
 	/*
 	 * Check till the allow max value for this mmap request
 	 */
@@ -322,12 +320,12 @@ static unsigned long slice_find_area_bottomup(struct mm_struct *mm,
 }
 
 static unsigned long slice_find_area_topdown(struct mm_struct *mm,
-					     unsigned long len,
+					     unsigned long addr, unsigned long len,
 					     const struct slice_mask *available,
 					     int psize, unsigned long high_limit)
 {
 	int pshift = max_t(int, mmu_psize_defs[psize].shift, PAGE_SHIFT);
-	unsigned long addr, found, prev;
+	unsigned long found, prev;
 	struct vm_unmapped_area_info info;
 	unsigned long min_addr = max(PAGE_SIZE, mmap_min_addr);
 
@@ -335,8 +333,6 @@ static unsigned long slice_find_area_topdown(struct mm_struct *mm,
 	info.length = len;
 	info.align_mask = PAGE_MASK & ((1ul << pshift) - 1);
 	info.align_offset = 0;
-
-	addr = mm->mmap_base;
 	/*
 	 * If we are trying to allocate above DEFAULT_MAP_WINDOW
 	 * Add the different to the mmap_base.
@@ -377,7 +373,7 @@ static unsigned long slice_find_area_topdown(struct mm_struct *mm,
 	 * can happen with large stack limits and large mmap()
 	 * allocations.
 	 */
-	return slice_find_area_bottomup(mm, len, available, psize, high_limit);
+	return slice_find_area_bottomup(mm, TASK_UNMAPPED_BASE, len, available, psize, high_limit);
 }
 
 
@@ -386,9 +382,9 @@ static unsigned long slice_find_area(struct mm_struct *mm, unsigned long len,
 				     int topdown, unsigned long high_limit)
 {
 	if (topdown)
-		return slice_find_area_topdown(mm, len, mask, psize, high_limit);
+		return slice_find_area_topdown(mm, mm->mmap_base, len, mask, psize, high_limit);
 	else
-		return slice_find_area_bottomup(mm, len, mask, psize, high_limit);
+		return slice_find_area_bottomup(mm, mm->mmap_base, len, mask, psize, high_limit);
 }
 
 static inline void slice_copy_mask(struct slice_mask *dst,
-- 
2.33.1

^ permalink raw reply related	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 03/10] powerpc/mm: Move vma_mmu_pagesize()
  2021-12-08 17:18 ` [PATCH v4 03/10] powerpc/mm: Move vma_mmu_pagesize() Christophe Leroy
@ 2021-12-09  9:36   ` Nicholas Piggin
  0 siblings, 0 replies; 27+ messages in thread
From: Nicholas Piggin @ 2021-12-09  9:36 UTC (permalink / raw)
  To: alex, Benjamin Herrenschmidt, Christophe Leroy, Michael Ellerman,
	Paul Mackerras
  Cc: akpm, linux-kernel, linux-mm, linuxppc-dev

Excerpts from Christophe Leroy's message of December 9, 2021 3:18 am:
> vma_mmu_pagesize() is only required for slices,
> otherwise there is a generic weak version doing the
> exact same thing.
> 
> Move it to slice.c
> 

Reviewed-by: Nicholas Piggin <npiggin@gmail.com>

> Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
> ---
>  arch/powerpc/mm/hugetlbpage.c | 11 -----------
>  arch/powerpc/mm/slice.c       |  9 +++++++++
>  2 files changed, 9 insertions(+), 11 deletions(-)
> 
> diff --git a/arch/powerpc/mm/hugetlbpage.c b/arch/powerpc/mm/hugetlbpage.c
> index ddead41e2194..0eec3b61bd13 100644
> --- a/arch/powerpc/mm/hugetlbpage.c
> +++ b/arch/powerpc/mm/hugetlbpage.c
> @@ -565,17 +565,6 @@ unsigned long hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
>  }
>  #endif
>  
> -unsigned long vma_mmu_pagesize(struct vm_area_struct *vma)
> -{
> -	/* With radix we don't use slice, so derive it from vma*/
> -	if (IS_ENABLED(CONFIG_PPC_MM_SLICES) && !radix_enabled()) {
> -		unsigned int psize = get_slice_psize(vma->vm_mm, vma->vm_start);
> -
> -		return 1UL << mmu_psize_to_shift(psize);
> -	}
> -	return vma_kernel_pagesize(vma);
> -}
> -
>  bool __init arch_hugetlb_valid_size(unsigned long size)
>  {
>  	int shift = __ffs(size);
> diff --git a/arch/powerpc/mm/slice.c b/arch/powerpc/mm/slice.c
> index f42711f865f3..8a3ac062b71e 100644
> --- a/arch/powerpc/mm/slice.c
> +++ b/arch/powerpc/mm/slice.c
> @@ -759,4 +759,13 @@ int slice_is_hugepage_only_range(struct mm_struct *mm, unsigned long addr,
>  
>  	return !slice_check_range_fits(mm, maskp, addr, len);
>  }
> +
> +unsigned long vma_mmu_pagesize(struct vm_area_struct *vma)
> +{
> +	/* With radix we don't use slice, so derive it from vma*/
> +	if (radix_enabled())
> +		return vma_kernel_pagesize(vma);
> +
> +	return 1UL << mmu_psize_to_shift(get_slice_psize(vma->vm_mm, vma->vm_start));
> +}
>  #endif
> -- 
> 2.33.1
> 
> 

^ permalink raw reply	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 02/10] mm, hugetlbfs: Allow an arch to always use generic versions of get_unmapped_area functions
  2021-12-08 17:18 ` [PATCH v4 02/10] mm, hugetlbfs: Allow an arch to always use generic versions of get_unmapped_area functions Christophe Leroy
@ 2021-12-09  9:40   ` Nicholas Piggin
  0 siblings, 0 replies; 27+ messages in thread
From: Nicholas Piggin @ 2021-12-09  9:40 UTC (permalink / raw)
  To: alex, Benjamin Herrenschmidt, Christophe Leroy, Michael Ellerman,
	Paul Mackerras
  Cc: akpm, linux-kernel, linux-mm, linuxppc-dev

Excerpts from Christophe Leroy's message of December 9, 2021 3:18 am:
> Unlike most architectures, powerpc can only define at runtime
> if it is going to use the generic arch_get_unmapped_area() or not.
> 
> Today, powerpc has a copy of the generic arch_get_unmapped_area()
> because when selection HAVE_ARCH_UNMAPPED_AREA the generic
> arch_get_unmapped_area() is not available.
> 
> Rename it generic_get_unmapped_area() and make it independent of
> HAVE_ARCH_UNMAPPED_AREA.
> 
> Do the same for arch_get_unmapped_area_topdown() versus
> HAVE_ARCH_UNMAPPED_AREA_TOPDOWN.
> 
> Do the same for hugetlb_get_unmapped_area() versus
> HAVE_ARCH_HUGETLB_UNMAPPED_AREA.
> 

Reviewed-by: Nicholas Piggin <npiggin@gmail.com>

> Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
> ---
>  fs/hugetlbfs/inode.c     | 17 +++++++++++++----
>  include/linux/hugetlb.h  |  5 +++++
>  include/linux/sched/mm.h |  9 +++++++++
>  mm/mmap.c                | 31 ++++++++++++++++++++++++-------
>  4 files changed, 51 insertions(+), 11 deletions(-)
> 

^ permalink raw reply	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 06/10] powerpc/mm: Use generic_get_unmapped_area() and call it from arch_get_unmapped_area()
  2021-12-08 17:18 ` [PATCH v4 06/10] powerpc/mm: Use generic_get_unmapped_area() and call it from arch_get_unmapped_area() Christophe Leroy
@ 2021-12-09  9:50   ` Nicholas Piggin
  2021-12-10 17:47     ` Christophe Leroy
  2021-12-16 14:25     ` Christophe Leroy
  2021-12-13 13:02   ` Michael Ellerman
  1 sibling, 2 replies; 27+ messages in thread
From: Nicholas Piggin @ 2021-12-09  9:50 UTC (permalink / raw)
  To: alex, Benjamin Herrenschmidt, Christophe Leroy, Michael Ellerman,
	Paul Mackerras
  Cc: akpm, linux-kernel, linux-mm, linuxppc-dev

Excerpts from Christophe Leroy's message of December 9, 2021 3:18 am:
> Use the generic version of arch_get_unmapped_area() which
> is now available at all time instead of its copy
> radix__arch_get_unmapped_area()
> 
> Instead of setting mm->get_unmapped_area() to either
> arch_get_unmapped_area() or generic_get_unmapped_area(),
> always set it to arch_get_unmapped_area() and call
> generic_get_unmapped_area() from there when radix is enabled.
> 
> Do the same with radix__arch_get_unmapped_area_topdown()
> 
> Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
> ---
>  arch/powerpc/mm/mmap.c | 127 ++---------------------------------------
>  1 file changed, 6 insertions(+), 121 deletions(-)
> 
> diff --git a/arch/powerpc/mm/mmap.c b/arch/powerpc/mm/mmap.c
> index 9b0d6e395bc0..46781d0103d1 100644
> --- a/arch/powerpc/mm/mmap.c
> +++ b/arch/powerpc/mm/mmap.c
> @@ -81,115 +81,15 @@ static inline unsigned long mmap_base(unsigned long rnd,
>  }
>  
>  #ifdef HAVE_ARCH_UNMAPPED_AREA
> -#ifdef CONFIG_PPC_RADIX_MMU
> -/*
> - * Same function as generic code used only for radix, because we don't need to overload
> - * the generic one. But we will have to duplicate, because hash select
> - * HAVE_ARCH_UNMAPPED_AREA
> - */
> -static unsigned long
> -radix__arch_get_unmapped_area(struct file *filp, unsigned long addr,
> -			     unsigned long len, unsigned long pgoff,
> -			     unsigned long flags)
> -{
> -	struct mm_struct *mm = current->mm;
> -	struct vm_area_struct *vma;
> -	int fixed = (flags & MAP_FIXED);
> -	unsigned long high_limit;
> -	struct vm_unmapped_area_info info;
> -
> -	high_limit = DEFAULT_MAP_WINDOW;
> -	if (addr >= high_limit || (fixed && (addr + len > high_limit)))
> -		high_limit = TASK_SIZE;

Does 64s radix need to define arch_get_mmap_end() to do the above now?

Otherwise great to consolidate this with core code, nice patch.

Thanks,
Nick


^ permalink raw reply	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 07/10] powerpc/mm: Use generic_hugetlb_get_unmapped_area()
  2021-12-08 17:18 ` [PATCH v4 07/10] powerpc/mm: Use generic_hugetlb_get_unmapped_area() Christophe Leroy
@ 2021-12-09 10:02   ` Nicholas Piggin
  2021-12-16 17:13     ` Christophe Leroy
  0 siblings, 1 reply; 27+ messages in thread
From: Nicholas Piggin @ 2021-12-09 10:02 UTC (permalink / raw)
  To: alex, Benjamin Herrenschmidt, Christophe Leroy, Michael Ellerman,
	Paul Mackerras
  Cc: akpm, linux-kernel, linux-mm, linuxppc-dev

Excerpts from Christophe Leroy's message of December 9, 2021 3:18 am:
> Use the generic version of arch_hugetlb_get_unmapped_area()
> which is now available at all time.
> 
> Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
> ---
>  arch/powerpc/include/asm/book3s/64/hugetlb.h |  4 --
>  arch/powerpc/mm/book3s64/radix_hugetlbpage.c | 55 --------------------
>  arch/powerpc/mm/hugetlbpage.c                |  4 +-
>  3 files changed, 1 insertion(+), 62 deletions(-)
> 
> diff --git a/arch/powerpc/include/asm/book3s/64/hugetlb.h b/arch/powerpc/include/asm/book3s/64/hugetlb.h
> index 12e150e615b7..b37a28f62cf6 100644
> --- a/arch/powerpc/include/asm/book3s/64/hugetlb.h
> +++ b/arch/powerpc/include/asm/book3s/64/hugetlb.h
> @@ -8,10 +8,6 @@
>   */
>  void radix__flush_hugetlb_page(struct vm_area_struct *vma, unsigned long vmaddr);
>  void radix__local_flush_hugetlb_page(struct vm_area_struct *vma, unsigned long vmaddr);
> -extern unsigned long
> -radix__hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
> -				unsigned long len, unsigned long pgoff,
> -				unsigned long flags);
>  
>  extern void radix__huge_ptep_modify_prot_commit(struct vm_area_struct *vma,
>  						unsigned long addr, pte_t *ptep,
> diff --git a/arch/powerpc/mm/book3s64/radix_hugetlbpage.c b/arch/powerpc/mm/book3s64/radix_hugetlbpage.c
> index 23d3e08911d3..d2fb776febb4 100644
> --- a/arch/powerpc/mm/book3s64/radix_hugetlbpage.c
> +++ b/arch/powerpc/mm/book3s64/radix_hugetlbpage.c
> @@ -41,61 +41,6 @@ void radix__flush_hugetlb_tlb_range(struct vm_area_struct *vma, unsigned long st
>  		radix__flush_tlb_range_psize(vma->vm_mm, start, end, psize);
>  }
>  
> -/*
> - * A vairant of hugetlb_get_unmapped_area doing topdown search
> - * FIXME!! should we do as x86 does or non hugetlb area does ?
> - * ie, use topdown or not based on mmap_is_legacy check ?
> - */
> -unsigned long
> -radix__hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
> -				unsigned long len, unsigned long pgoff,
> -				unsigned long flags)
> -{
> -	struct mm_struct *mm = current->mm;
> -	struct vm_area_struct *vma;
> -	struct hstate *h = hstate_file(file);
> -	int fixed = (flags & MAP_FIXED);
> -	unsigned long high_limit;
> -	struct vm_unmapped_area_info info;
> -
> -	high_limit = DEFAULT_MAP_WINDOW;
> -	if (addr >= high_limit || (fixed && (addr + len > high_limit)))
> -		high_limit = TASK_SIZE;

I wonder if generic hugetlb_get_unmapped_area needs to have the
arch_get_mmap_end() added.

arm64 has arch_get_mmap_end() and !HAVE_ARCH_HUGETLB_UNMAPPED_AREA so
it looks like it has broken large address hint logic for hugetlbfs
mappings? x86-64 defines their own and does the same hinting for
normal and hugetlbfs mmap.

If we had that and defied arch_get_mmap_end(), then this patch should
work.

Thanks,
Nick

^ permalink raw reply	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 09/10] powerpc/mm: Convert to default topdown mmap layout
  2021-12-08 17:18 ` [PATCH v4 09/10] powerpc/mm: Convert to default topdown mmap layout Christophe Leroy
@ 2021-12-09 10:15   ` Nicholas Piggin
  2021-12-09 10:22     ` Christophe Leroy
  2021-12-16 14:27     ` Christophe Leroy
  0 siblings, 2 replies; 27+ messages in thread
From: Nicholas Piggin @ 2021-12-09 10:15 UTC (permalink / raw)
  To: alex, Benjamin Herrenschmidt, Christophe Leroy, Michael Ellerman,
	Paul Mackerras
  Cc: akpm, linux-kernel, linux-mm, linuxppc-dev

Excerpts from Christophe Leroy's message of December 9, 2021 3:18 am:
> Select CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT and
> remove arch/powerpc/mm/mmap.c
> 
> This change provides standard randomisation of mmaps.
> 
> See commit 8b8addf891de ("x86/mm/32: Enable full randomization on i386
> and X86_32") for all the benefits of mmap randomisation.

The justification seems pretty reasonable.

> 
> Comparison between powerpc implementation and the generic one:
> - mmap_is_legacy() is identical.
> - arch_mmap_rnd() does exactly the same allthough it's written
> slightly differently.
> - MIN_GAP and MAX_GAP are identical.
> - mmap_base() does the same but uses STACK_RND_MASK which provides
> the same values as stack_maxrandom_size().
> - arch_pick_mmap_layout() is almost identical. The only difference
> is that it also adds the random factor to mm->mmap_base in legacy mode.
> 
> That last point is what provides the standard randomisation of mmaps.

Thanks for describing it. Could you add random_factor to mmap_base for
the legacy path for powerpc as a 2-line change that adds the legacy
randomisation. And then this bigger patch would be closer to a no-op.

Thanks,
Nick


^ permalink raw reply	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 09/10] powerpc/mm: Convert to default topdown mmap layout
  2021-12-09 10:15   ` Nicholas Piggin
@ 2021-12-09 10:22     ` Christophe Leroy
  2021-12-09 10:43       ` Nicholas Piggin
  2021-12-16 14:27     ` Christophe Leroy
  1 sibling, 1 reply; 27+ messages in thread
From: Christophe Leroy @ 2021-12-09 10:22 UTC (permalink / raw)
  To: Nicholas Piggin, alex, Benjamin Herrenschmidt, Michael Ellerman,
	Paul Mackerras
  Cc: akpm, linux-kernel, linux-mm, linuxppc-dev



Le 09/12/2021 à 11:15, Nicholas Piggin a écrit :
> Excerpts from Christophe Leroy's message of December 9, 2021 3:18 am:
>> Select CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT and
>> remove arch/powerpc/mm/mmap.c
>>
>> This change provides standard randomisation of mmaps.
>>
>> See commit 8b8addf891de ("x86/mm/32: Enable full randomization on i386
>> and X86_32") for all the benefits of mmap randomisation.
> 
> The justification seems pretty reasonable.
> 
>>
>> Comparison between powerpc implementation and the generic one:
>> - mmap_is_legacy() is identical.
>> - arch_mmap_rnd() does exactly the same allthough it's written
>> slightly differently.
>> - MIN_GAP and MAX_GAP are identical.
>> - mmap_base() does the same but uses STACK_RND_MASK which provides
>> the same values as stack_maxrandom_size().
>> - arch_pick_mmap_layout() is almost identical. The only difference
>> is that it also adds the random factor to mm->mmap_base in legacy mode.
>>
>> That last point is what provides the standard randomisation of mmaps.
> 
> Thanks for describing it. Could you add random_factor to mmap_base for
> the legacy path for powerpc as a 2-line change that adds the legacy
> randomisation. And then this bigger patch would be closer to a no-op.
> 

You mean you would like to see the following patch before doing the 
convert ?

https://patchwork.ozlabs.org/project/linuxppc-dev/patch/7dabf1cbde67a346a187881d4f0bd17347e0334a.1533732583.git.christophe.leroy@c-s.fr/

^ permalink raw reply	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 09/10] powerpc/mm: Convert to default topdown mmap layout
  2021-12-09 10:22     ` Christophe Leroy
@ 2021-12-09 10:43       ` Nicholas Piggin
  2021-12-09 11:22         ` Michael Ellerman
  0 siblings, 1 reply; 27+ messages in thread
From: Nicholas Piggin @ 2021-12-09 10:43 UTC (permalink / raw)
  To: alex, Benjamin Herrenschmidt, Christophe Leroy, Michael Ellerman,
	Paul Mackerras
  Cc: akpm, linux-kernel, linux-mm, linuxppc-dev

Excerpts from Christophe Leroy's message of December 9, 2021 8:22 pm:
> 
> 
> Le 09/12/2021 à 11:15, Nicholas Piggin a écrit :
>> Excerpts from Christophe Leroy's message of December 9, 2021 3:18 am:
>>> Select CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT and
>>> remove arch/powerpc/mm/mmap.c
>>>
>>> This change provides standard randomisation of mmaps.
>>>
>>> See commit 8b8addf891de ("x86/mm/32: Enable full randomization on i386
>>> and X86_32") for all the benefits of mmap randomisation.
>> 
>> The justification seems pretty reasonable.
>> 
>>>
>>> Comparison between powerpc implementation and the generic one:
>>> - mmap_is_legacy() is identical.
>>> - arch_mmap_rnd() does exactly the same allthough it's written
>>> slightly differently.
>>> - MIN_GAP and MAX_GAP are identical.
>>> - mmap_base() does the same but uses STACK_RND_MASK which provides
>>> the same values as stack_maxrandom_size().
>>> - arch_pick_mmap_layout() is almost identical. The only difference
>>> is that it also adds the random factor to mm->mmap_base in legacy mode.
>>>
>>> That last point is what provides the standard randomisation of mmaps.
>> 
>> Thanks for describing it. Could you add random_factor to mmap_base for
>> the legacy path for powerpc as a 2-line change that adds the legacy
>> randomisation. And then this bigger patch would be closer to a no-op.
>> 
> 
> You mean you would like to see the following patch before doing the 
> convert ?
> 
> https://patchwork.ozlabs.org/project/linuxppc-dev/patch/7dabf1cbde67a346a187881d4f0bd17347e0334a.1533732583.git.christophe.leroy@c-s.fr/

Yes.

Thanks,
Nick

^ permalink raw reply	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 09/10] powerpc/mm: Convert to default topdown mmap layout
  2021-12-09 10:43       ` Nicholas Piggin
@ 2021-12-09 11:22         ` Michael Ellerman
  2021-12-09 11:32           ` Christophe Leroy
  0 siblings, 1 reply; 27+ messages in thread
From: Michael Ellerman @ 2021-12-09 11:22 UTC (permalink / raw)
  To: Nicholas Piggin, alex, Benjamin Herrenschmidt, Christophe Leroy,
	Paul Mackerras
  Cc: akpm, linux-kernel, linux-mm, linuxppc-dev

Nicholas Piggin <npiggin@gmail.com> writes:

> Excerpts from Christophe Leroy's message of December 9, 2021 8:22 pm:
>> 
>> 
>> Le 09/12/2021 à 11:15, Nicholas Piggin a écrit :
>>> Excerpts from Christophe Leroy's message of December 9, 2021 3:18 am:
>>>> Select CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT and
>>>> remove arch/powerpc/mm/mmap.c
>>>>
>>>> This change provides standard randomisation of mmaps.
>>>>
>>>> See commit 8b8addf891de ("x86/mm/32: Enable full randomization on i386
>>>> and X86_32") for all the benefits of mmap randomisation.
>>> 
>>> The justification seems pretty reasonable.
>>> 
>>>>
>>>> Comparison between powerpc implementation and the generic one:
>>>> - mmap_is_legacy() is identical.
>>>> - arch_mmap_rnd() does exactly the same allthough it's written
>>>> slightly differently.
>>>> - MIN_GAP and MAX_GAP are identical.
>>>> - mmap_base() does the same but uses STACK_RND_MASK which provides
>>>> the same values as stack_maxrandom_size().
>>>> - arch_pick_mmap_layout() is almost identical. The only difference
>>>> is that it also adds the random factor to mm->mmap_base in legacy mode.
>>>>
>>>> That last point is what provides the standard randomisation of mmaps.
>>> 
>>> Thanks for describing it. Could you add random_factor to mmap_base for
>>> the legacy path for powerpc as a 2-line change that adds the legacy
>>> randomisation. And then this bigger patch would be closer to a no-op.
>>> 
>> 
>> You mean you would like to see the following patch before doing the 
>> convert ?
>> 
>> https://patchwork.ozlabs.org/project/linuxppc-dev/patch/7dabf1cbde67a346a187881d4f0bd17347e0334a.1533732583.git.christophe.leroy@c-s.fr/
>
> Yes.

My comment at the time was:

  Basically mmap_is_legacy() tells you if any of these is true:
  
   - process has the ADDR_COMPAT_LAYOUT personality
   - global legacy_va_layout sysctl is enabled
   - stack is unlimited

  And we only want to change the behaviour for the stack. Or at least the
  change log of your patch only talks about the stack limit, not the
  others.
  
  Possibly we should just enable randomisation for all three of those
  cases, but if so we must spell it out in the patch.
  
  It'd also be good to see the output of /proc/x/maps for some processes
  before and after, to show what actually changes.


From: https://github.com/linuxppc/issues/issues/59#issuecomment-502066947


So I think at least the change log on that patch still needs updating to
be clear that it's changing behaviour for all mmap_is_legacy() cases,
not just the stack unlimited case.

There's also a risk changing the mmap legacy behaviour breaks something.
But we are at least matching the behaviour of other architectures, and
there is also an escape hatch in the form of `setarch -R`.

cheers


^ permalink raw reply	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 09/10] powerpc/mm: Convert to default topdown mmap layout
  2021-12-09 11:22         ` Michael Ellerman
@ 2021-12-09 11:32           ` Christophe Leroy
  2021-12-09 23:56             ` Michael Ellerman
  0 siblings, 1 reply; 27+ messages in thread
From: Christophe Leroy @ 2021-12-09 11:32 UTC (permalink / raw)
  To: Michael Ellerman, Nicholas Piggin, alex, Benjamin Herrenschmidt,
	Paul Mackerras
  Cc: akpm, linux-kernel, linux-mm, linuxppc-dev



Le 09/12/2021 à 12:22, Michael Ellerman a écrit :
> Nicholas Piggin <npiggin@gmail.com> writes:
> 
>> Excerpts from Christophe Leroy's message of December 9, 2021 8:22 pm:
>>>
>>>
>>> Le 09/12/2021 à 11:15, Nicholas Piggin a écrit :
>>>> Excerpts from Christophe Leroy's message of December 9, 2021 3:18 am:
>>>>> Select CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT and
>>>>> remove arch/powerpc/mm/mmap.c
>>>>>
>>>>> This change provides standard randomisation of mmaps.
>>>>>
>>>>> See commit 8b8addf891de ("x86/mm/32: Enable full randomization on i386
>>>>> and X86_32") for all the benefits of mmap randomisation.
>>>>
>>>> The justification seems pretty reasonable.
>>>>
>>>>>
>>>>> Comparison between powerpc implementation and the generic one:
>>>>> - mmap_is_legacy() is identical.
>>>>> - arch_mmap_rnd() does exactly the same allthough it's written
>>>>> slightly differently.
>>>>> - MIN_GAP and MAX_GAP are identical.
>>>>> - mmap_base() does the same but uses STACK_RND_MASK which provides
>>>>> the same values as stack_maxrandom_size().
>>>>> - arch_pick_mmap_layout() is almost identical. The only difference
>>>>> is that it also adds the random factor to mm->mmap_base in legacy mode.
>>>>>
>>>>> That last point is what provides the standard randomisation of mmaps.
>>>>
>>>> Thanks for describing it. Could you add random_factor to mmap_base for
>>>> the legacy path for powerpc as a 2-line change that adds the legacy
>>>> randomisation. And then this bigger patch would be closer to a no-op.
>>>>
>>>
>>> You mean you would like to see the following patch before doing the
>>> convert ?
>>>
>>> https://patchwork.ozlabs.org/project/linuxppc-dev/patch/7dabf1cbde67a346a187881d4f0bd17347e0334a.1533732583.git.christophe.leroy@c-s.fr/
>>
>> Yes.
> 
> My comment at the time was:
> 
>    Basically mmap_is_legacy() tells you if any of these is true:
>    
>     - process has the ADDR_COMPAT_LAYOUT personality
>     - global legacy_va_layout sysctl is enabled
>     - stack is unlimited
> 
>    And we only want to change the behaviour for the stack. Or at least the
>    change log of your patch only talks about the stack limit, not the
>    others.
>    
>    Possibly we should just enable randomisation for all three of those
>    cases, but if so we must spell it out in the patch.
>    
>    It'd also be good to see the output of /proc/x/maps for some processes
>    before and after, to show what actually changes.
> 
> 
> From: https://github.com/linuxppc/issues/issues/59#issuecomment-502066947
> 
> 
> So I think at least the change log on that patch still needs updating to
> be clear that it's changing behaviour for all mmap_is_legacy() cases,
> not just the stack unlimited case.
> 
> There's also a risk changing the mmap legacy behaviour breaks something.
> But we are at least matching the behaviour of other architectures, and
> there is also an escape hatch in the form of `setarch -R`.
> 

That was the purpose of adding in the change log a reference to commit 
8b8addf891de ("x86/mm/32: Enable full randomization on i386
and X86_32")

All this applies to powerpc as well.

But I can copy paste the changelog of that commit into mine if you think 
it is more explicit.

I agree that old patch was only refering to stack limit, I had no clue 
of everything else at that time.

Christophe

^ permalink raw reply	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 09/10] powerpc/mm: Convert to default topdown mmap layout
  2021-12-09 11:32           ` Christophe Leroy
@ 2021-12-09 23:56             ` Michael Ellerman
  0 siblings, 0 replies; 27+ messages in thread
From: Michael Ellerman @ 2021-12-09 23:56 UTC (permalink / raw)
  To: Christophe Leroy, Nicholas Piggin, alex, Benjamin Herrenschmidt,
	Paul Mackerras
  Cc: akpm, linux-kernel, linux-mm, linuxppc-dev

Christophe Leroy <christophe.leroy@csgroup.eu> writes:
> Le 09/12/2021 à 12:22, Michael Ellerman a écrit :
>> Nicholas Piggin <npiggin@gmail.com> writes:
>> 
>>> Excerpts from Christophe Leroy's message of December 9, 2021 8:22 pm:
>>>>
>>>>
>>>> Le 09/12/2021 à 11:15, Nicholas Piggin a écrit :
>>>>> Excerpts from Christophe Leroy's message of December 9, 2021 3:18 am:
>>>>>> Select CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT and
>>>>>> remove arch/powerpc/mm/mmap.c
>>>>>>
>>>>>> This change provides standard randomisation of mmaps.
>>>>>>
>>>>>> See commit 8b8addf891de ("x86/mm/32: Enable full randomization on i386
>>>>>> and X86_32") for all the benefits of mmap randomisation.
>>>>>
>>>>> The justification seems pretty reasonable.
>>>>>
>>>>>>
>>>>>> Comparison between powerpc implementation and the generic one:
>>>>>> - mmap_is_legacy() is identical.
>>>>>> - arch_mmap_rnd() does exactly the same allthough it's written
>>>>>> slightly differently.
>>>>>> - MIN_GAP and MAX_GAP are identical.
>>>>>> - mmap_base() does the same but uses STACK_RND_MASK which provides
>>>>>> the same values as stack_maxrandom_size().
>>>>>> - arch_pick_mmap_layout() is almost identical. The only difference
>>>>>> is that it also adds the random factor to mm->mmap_base in legacy mode.
>>>>>>
>>>>>> That last point is what provides the standard randomisation of mmaps.
>>>>>
>>>>> Thanks for describing it. Could you add random_factor to mmap_base for
>>>>> the legacy path for powerpc as a 2-line change that adds the legacy
>>>>> randomisation. And then this bigger patch would be closer to a no-op.
>>>>>
>>>>
>>>> You mean you would like to see the following patch before doing the
>>>> convert ?
>>>>
>>>> https://patchwork.ozlabs.org/project/linuxppc-dev/patch/7dabf1cbde67a346a187881d4f0bd17347e0334a.1533732583.git.christophe.leroy@c-s.fr/
>>>
>>> Yes.
>> 
>> My comment at the time was:
>> 
>>    Basically mmap_is_legacy() tells you if any of these is true:
>>    
>>     - process has the ADDR_COMPAT_LAYOUT personality
>>     - global legacy_va_layout sysctl is enabled
>>     - stack is unlimited
>> 
>>    And we only want to change the behaviour for the stack. Or at least the
>>    change log of your patch only talks about the stack limit, not the
>>    others.
>>    
>>    Possibly we should just enable randomisation for all three of those
>>    cases, but if so we must spell it out in the patch.
>>    
>>    It'd also be good to see the output of /proc/x/maps for some processes
>>    before and after, to show what actually changes.
>> 
>> 
>> From: https://github.com/linuxppc/issues/issues/59#issuecomment-502066947
>> 
>> 
>> So I think at least the change log on that patch still needs updating to
>> be clear that it's changing behaviour for all mmap_is_legacy() cases,
>> not just the stack unlimited case.
>> 
>> There's also a risk changing the mmap legacy behaviour breaks something.
>> But we are at least matching the behaviour of other architectures, and
>> there is also an escape hatch in the form of `setarch -R`.
>
> That was the purpose of adding in the change log a reference to commit 
> 8b8addf891de ("x86/mm/32: Enable full randomization on i386
> and X86_32")
>
> All this applies to powerpc as well.

Yeah, I'm just a pessimist :) So although the security benefit is nice,
I'm more worried that the layout change will break some mission critical
legacy app somewhere. So I just like to have that spelled out in the
change log, or at least in the discussion like here.

> But I can copy paste the changelog of that commit into mine if you think 
> it is more explicit.

Just referring to it is probably fine.

> I agree that old patch was only refering to stack limit, I had no clue 
> of everything else at that time.

No worries.

cheers

^ permalink raw reply	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 06/10] powerpc/mm: Use generic_get_unmapped_area() and call it from arch_get_unmapped_area()
  2021-12-09  9:50   ` Nicholas Piggin
@ 2021-12-10 17:47     ` Christophe Leroy
  2021-12-16 14:25     ` Christophe Leroy
  1 sibling, 0 replies; 27+ messages in thread
From: Christophe Leroy @ 2021-12-10 17:47 UTC (permalink / raw)
  To: Nicholas Piggin, alex, Benjamin Herrenschmidt, Michael Ellerman,
	Paul Mackerras
  Cc: akpm, linux-kernel, linux-mm, linuxppc-dev



Le 09/12/2021 à 10:50, Nicholas Piggin a écrit :
> Excerpts from Christophe Leroy's message of December 9, 2021 3:18 am:
>> Use the generic version of arch_get_unmapped_area() which
>> is now available at all time instead of its copy
>> radix__arch_get_unmapped_area()
>>
>> Instead of setting mm->get_unmapped_area() to either
>> arch_get_unmapped_area() or generic_get_unmapped_area(),
>> always set it to arch_get_unmapped_area() and call
>> generic_get_unmapped_area() from there when radix is enabled.
>>
>> Do the same with radix__arch_get_unmapped_area_topdown()
>>
>> Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
>> ---
>>   arch/powerpc/mm/mmap.c | 127 ++---------------------------------------
>>   1 file changed, 6 insertions(+), 121 deletions(-)
>>
>> diff --git a/arch/powerpc/mm/mmap.c b/arch/powerpc/mm/mmap.c
>> index 9b0d6e395bc0..46781d0103d1 100644
>> --- a/arch/powerpc/mm/mmap.c
>> +++ b/arch/powerpc/mm/mmap.c
>> @@ -81,115 +81,15 @@ static inline unsigned long mmap_base(unsigned long rnd,
>>   }
>>   
>>   #ifdef HAVE_ARCH_UNMAPPED_AREA
>> -#ifdef CONFIG_PPC_RADIX_MMU
>> -/*
>> - * Same function as generic code used only for radix, because we don't need to overload
>> - * the generic one. But we will have to duplicate, because hash select
>> - * HAVE_ARCH_UNMAPPED_AREA
>> - */
>> -static unsigned long
>> -radix__arch_get_unmapped_area(struct file *filp, unsigned long addr,
>> -			     unsigned long len, unsigned long pgoff,
>> -			     unsigned long flags)
>> -{
>> -	struct mm_struct *mm = current->mm;
>> -	struct vm_area_struct *vma;
>> -	int fixed = (flags & MAP_FIXED);
>> -	unsigned long high_limit;
>> -	struct vm_unmapped_area_info info;
>> -
>> -	high_limit = DEFAULT_MAP_WINDOW;
>> -	if (addr >= high_limit || (fixed && (addr + len > high_limit)))
>> -		high_limit = TASK_SIZE;
> 
> Does 64s radix need to define arch_get_mmap_end() to do the above now?

Sure, good point.

Seems like I got hypnotised by the comment "- * Same function as generic 
code used only for radix", I didn't catch that little difference.

> 
> Otherwise great to consolidate this with core code, nice patch.
> 
> Thanks,
> Nick
> 

^ permalink raw reply	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 06/10] powerpc/mm: Use generic_get_unmapped_area() and call it from arch_get_unmapped_area()
  2021-12-08 17:18 ` [PATCH v4 06/10] powerpc/mm: Use generic_get_unmapped_area() and call it from arch_get_unmapped_area() Christophe Leroy
  2021-12-09  9:50   ` Nicholas Piggin
@ 2021-12-13 13:02   ` Michael Ellerman
  1 sibling, 0 replies; 27+ messages in thread
From: Michael Ellerman @ 2021-12-13 13:02 UTC (permalink / raw)
  To: Christophe Leroy, Benjamin Herrenschmidt, Paul Mackerras, alex
  Cc: Christophe Leroy, linux-kernel, linuxppc-dev, linux-mm, akpm

Christophe Leroy <christophe.leroy@csgroup.eu> writes:
> Use the generic version of arch_get_unmapped_area() which
> is now available at all time instead of its copy
> radix__arch_get_unmapped_area()
>
> Instead of setting mm->get_unmapped_area() to either
> arch_get_unmapped_area() or generic_get_unmapped_area(),
> always set it to arch_get_unmapped_area() and call
> generic_get_unmapped_area() from there when radix is enabled.
>
> Do the same with radix__arch_get_unmapped_area_topdown()
>
> Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
> ---
>  arch/powerpc/mm/mmap.c | 127 ++---------------------------------------
>  1 file changed, 6 insertions(+), 121 deletions(-)
>
> diff --git a/arch/powerpc/mm/mmap.c b/arch/powerpc/mm/mmap.c
> index 9b0d6e395bc0..46781d0103d1 100644
> --- a/arch/powerpc/mm/mmap.c
> +++ b/arch/powerpc/mm/mmap.c
> @@ -81,115 +81,15 @@ static inline unsigned long mmap_base(unsigned long rnd,
>  }
>  
>  #ifdef HAVE_ARCH_UNMAPPED_AREA
> -#ifdef CONFIG_PPC_RADIX_MMU
> -/*
> - * Same function as generic code used only for radix, because we don't need to overload
> - * the generic one. But we will have to duplicate, because hash select
> - * HAVE_ARCH_UNMAPPED_AREA
> - */
> -static unsigned long
> -radix__arch_get_unmapped_area(struct file *filp, unsigned long addr,
> -			     unsigned long len, unsigned long pgoff,
> -			     unsigned long flags)
> -{
> -	struct mm_struct *mm = current->mm;
> -	struct vm_area_struct *vma;
> -	int fixed = (flags & MAP_FIXED);
> -	unsigned long high_limit;
> -	struct vm_unmapped_area_info info;
> -
> -	high_limit = DEFAULT_MAP_WINDOW;
> -	if (addr >= high_limit || (fixed && (addr + len > high_limit)))
> -		high_limit = TASK_SIZE;
> -
> -	if (len > high_limit)
> -		return -ENOMEM;

There are some differences in the above vs the generic code, the generic
arch_get_unmapped_area_topdown() in mm/mmap.c does:

	const unsigned long mmap_end = arch_get_mmap_end(addr);

	if (len > mmap_end - mmap_min_addr)
		return -ENOMEM;

	if (flags & MAP_FIXED)
		return addr;


Our current code adjusts high_limit for fixed mappings that span above
the default map window. We added that logic in:

  35602f82d0c7 ("powerpc/64s/hash: Allow MAP_FIXED allocations to cross 128TB boundary")

That means a fixed mapping that crosses the 128T boundary will be
allowed by our code.

On the other hand the generic code will allow a fixed mapping to cross
the 128T boundary, but only if the size of the mapping is < ~128T.

(The actual size limit is (128T - mmap_min_addr), which is usually 4K or
64K, but is adjustable.)

It's unlikely that any apps are doing fixed mappings larger than 128T
that cross the 128T boundary, but I think we need to allow it. 128T
seems like a lot, but is not compared to the entire 4PB address space.

So I think we need to fix that in the generic code.

The easiest option is probably to pass flags to arch_get_mmap_end(), and
then the arches can decide whether to adjust the return value based on
flags.


Then there's also the extra check we have here:

> -	if (fixed) {
> -		if (addr > high_limit - len)
> -			return -ENOMEM;
> -		return addr;
> -	}

I think we can drop that when converting to the generic version, the
only case in which it matters is when high_limit == TASK_SIZE, and
get_unmapped_area() already does that check after calling us:

	if (addr > TASK_SIZE - len)
		return -ENOMEM;


cheers

^ permalink raw reply	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 06/10] powerpc/mm: Use generic_get_unmapped_area() and call it from arch_get_unmapped_area()
  2021-12-09  9:50   ` Nicholas Piggin
  2021-12-10 17:47     ` Christophe Leroy
@ 2021-12-16 14:25     ` Christophe Leroy
  1 sibling, 0 replies; 27+ messages in thread
From: Christophe Leroy @ 2021-12-16 14:25 UTC (permalink / raw)
  To: Nicholas Piggin, alex, Benjamin Herrenschmidt, Michael Ellerman,
	Paul Mackerras
  Cc: akpm, linux-kernel, linux-mm, linuxppc-dev



Le 09/12/2021 à 10:50, Nicholas Piggin a écrit :
> Excerpts from Christophe Leroy's message of December 9, 2021 3:18 am:
>> Use the generic version of arch_get_unmapped_area() which
>> is now available at all time instead of its copy
>> radix__arch_get_unmapped_area()
>>
>> Instead of setting mm->get_unmapped_area() to either
>> arch_get_unmapped_area() or generic_get_unmapped_area(),
>> always set it to arch_get_unmapped_area() and call
>> generic_get_unmapped_area() from there when radix is enabled.
>>
>> Do the same with radix__arch_get_unmapped_area_topdown()
>>
>> Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
>> ---
>>   arch/powerpc/mm/mmap.c | 127 ++---------------------------------------
>>   1 file changed, 6 insertions(+), 121 deletions(-)
>>
>> diff --git a/arch/powerpc/mm/mmap.c b/arch/powerpc/mm/mmap.c
>> index 9b0d6e395bc0..46781d0103d1 100644
>> --- a/arch/powerpc/mm/mmap.c
>> +++ b/arch/powerpc/mm/mmap.c
>> @@ -81,115 +81,15 @@ static inline unsigned long mmap_base(unsigned long rnd,
>>   }
>>   
>>   #ifdef HAVE_ARCH_UNMAPPED_AREA
>> -#ifdef CONFIG_PPC_RADIX_MMU
>> -/*
>> - * Same function as generic code used only for radix, because we don't need to overload
>> - * the generic one. But we will have to duplicate, because hash select
>> - * HAVE_ARCH_UNMAPPED_AREA
>> - */
>> -static unsigned long
>> -radix__arch_get_unmapped_area(struct file *filp, unsigned long addr,
>> -			     unsigned long len, unsigned long pgoff,
>> -			     unsigned long flags)
>> -{
>> -	struct mm_struct *mm = current->mm;
>> -	struct vm_area_struct *vma;
>> -	int fixed = (flags & MAP_FIXED);
>> -	unsigned long high_limit;
>> -	struct vm_unmapped_area_info info;
>> -
>> -	high_limit = DEFAULT_MAP_WINDOW;
>> -	if (addr >= high_limit || (fixed && (addr + len > high_limit)))
>> -		high_limit = TASK_SIZE;
> 
> Does 64s radix need to define arch_get_mmap_end() to do the above now?
> 
> Otherwise great to consolidate this with core code, nice patch.
> 

Yes it needs arch_get_mmap_end() and also arch_get_mmap_base().

I added it in v5, taking also suggestion from Michael.

Thanks
Christophe

^ permalink raw reply	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 09/10] powerpc/mm: Convert to default topdown mmap layout
  2021-12-09 10:15   ` Nicholas Piggin
  2021-12-09 10:22     ` Christophe Leroy
@ 2021-12-16 14:27     ` Christophe Leroy
  1 sibling, 0 replies; 27+ messages in thread
From: Christophe Leroy @ 2021-12-16 14:27 UTC (permalink / raw)
  To: Nicholas Piggin, alex, Benjamin Herrenschmidt, Michael Ellerman,
	Paul Mackerras
  Cc: akpm, linux-kernel, linux-mm, linuxppc-dev



Le 09/12/2021 à 11:15, Nicholas Piggin a écrit :
> Excerpts from Christophe Leroy's message of December 9, 2021 3:18 am:
>> Select CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT and
>> remove arch/powerpc/mm/mmap.c
>>
>> This change provides standard randomisation of mmaps.
>>
>> See commit 8b8addf891de ("x86/mm/32: Enable full randomization on i386
>> and X86_32") for all the benefits of mmap randomisation.
> 
> The justification seems pretty reasonable.
> 
>>
>> Comparison between powerpc implementation and the generic one:
>> - mmap_is_legacy() is identical.
>> - arch_mmap_rnd() does exactly the same allthough it's written
>> slightly differently.
>> - MIN_GAP and MAX_GAP are identical.
>> - mmap_base() does the same but uses STACK_RND_MASK which provides
>> the same values as stack_maxrandom_size().
>> - arch_pick_mmap_layout() is almost identical. The only difference
>> is that it also adds the random factor to mm->mmap_base in legacy mode.
>>
>> That last point is what provides the standard randomisation of mmaps.
> 
> Thanks for describing it. Could you add random_factor to mmap_base for
> the legacy path for powerpc as a 2-line change that adds the legacy
> randomisation. And then this bigger patch would be closer to a no-op.
> 

Ok, in v5 I added that change in patch 10 then switched this patch with 
that patch.

Christophe

^ permalink raw reply	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 07/10] powerpc/mm: Use generic_hugetlb_get_unmapped_area()
  2021-12-09 10:02   ` Nicholas Piggin
@ 2021-12-16 17:13     ` Christophe Leroy
  2021-12-16 18:55       ` Catalin Marinas
  0 siblings, 1 reply; 27+ messages in thread
From: Christophe Leroy @ 2021-12-16 17:13 UTC (permalink / raw)
  To: Nicholas Piggin, alex, Benjamin Herrenschmidt, Michael Ellerman,
	Paul Mackerras, Will Deacon, Catalin Marinas, Steve Capper
  Cc: akpm, linux-kernel, linux-mm, linuxppc-dev, Linux ARM



Le 09/12/2021 à 11:02, Nicholas Piggin a écrit :
> Excerpts from Christophe Leroy's message of December 9, 2021 3:18 am:
>> Use the generic version of arch_hugetlb_get_unmapped_area()
>> which is now available at all time.
>>
>> Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
>> ---
>>   arch/powerpc/include/asm/book3s/64/hugetlb.h |  4 --
>>   arch/powerpc/mm/book3s64/radix_hugetlbpage.c | 55 --------------------
>>   arch/powerpc/mm/hugetlbpage.c                |  4 +-
>>   3 files changed, 1 insertion(+), 62 deletions(-)
>>
>> diff --git a/arch/powerpc/include/asm/book3s/64/hugetlb.h b/arch/powerpc/include/asm/book3s/64/hugetlb.h
>> index 12e150e615b7..b37a28f62cf6 100644
>> --- a/arch/powerpc/include/asm/book3s/64/hugetlb.h
>> +++ b/arch/powerpc/include/asm/book3s/64/hugetlb.h
>> @@ -8,10 +8,6 @@
>>    */
>>   void radix__flush_hugetlb_page(struct vm_area_struct *vma, unsigned long vmaddr);
>>   void radix__local_flush_hugetlb_page(struct vm_area_struct *vma, unsigned long vmaddr);
>> -extern unsigned long
>> -radix__hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
>> -				unsigned long len, unsigned long pgoff,
>> -				unsigned long flags);
>>   
>>   extern void radix__huge_ptep_modify_prot_commit(struct vm_area_struct *vma,
>>   						unsigned long addr, pte_t *ptep,
>> diff --git a/arch/powerpc/mm/book3s64/radix_hugetlbpage.c b/arch/powerpc/mm/book3s64/radix_hugetlbpage.c
>> index 23d3e08911d3..d2fb776febb4 100644
>> --- a/arch/powerpc/mm/book3s64/radix_hugetlbpage.c
>> +++ b/arch/powerpc/mm/book3s64/radix_hugetlbpage.c
>> @@ -41,61 +41,6 @@ void radix__flush_hugetlb_tlb_range(struct vm_area_struct *vma, unsigned long st
>>   		radix__flush_tlb_range_psize(vma->vm_mm, start, end, psize);
>>   }
>>   
>> -/*
>> - * A vairant of hugetlb_get_unmapped_area doing topdown search
>> - * FIXME!! should we do as x86 does or non hugetlb area does ?
>> - * ie, use topdown or not based on mmap_is_legacy check ?
>> - */
>> -unsigned long
>> -radix__hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
>> -				unsigned long len, unsigned long pgoff,
>> -				unsigned long flags)
>> -{
>> -	struct mm_struct *mm = current->mm;
>> -	struct vm_area_struct *vma;
>> -	struct hstate *h = hstate_file(file);
>> -	int fixed = (flags & MAP_FIXED);
>> -	unsigned long high_limit;
>> -	struct vm_unmapped_area_info info;
>> -
>> -	high_limit = DEFAULT_MAP_WINDOW;
>> -	if (addr >= high_limit || (fixed && (addr + len > high_limit)))
>> -		high_limit = TASK_SIZE;
> 
> I wonder if generic hugetlb_get_unmapped_area needs to have the
> arch_get_mmap_end() added.
> 
> arm64 has arch_get_mmap_end() and !HAVE_ARCH_HUGETLB_UNMAPPED_AREA so
> it looks like it has broken large address hint logic for hugetlbfs
> mappings? x86-64 defines their own and does the same hinting for
> normal and hugetlbfs mmap.
> 
> If we had that and defied arch_get_mmap_end(), then this patch should
> work.
> 

As far as I can see, hugetlb_get_unmapped_area() variants used to be 
very similar to get_unmapped_area() until commit 1be7107fbe18 ("mm: 
larger stack guard gap, between vmas") and commit f6795053dac8 ("mm: 
mmap: Allow for "high" userspace addresses")

I see no reason why those changes couldn't apply to 
hugetlb_get_unmapped_area() as well.

Need to know what ARM64 think about it thought. Will, Catalin, any opinion ?

Christophe

^ permalink raw reply	[flat|nested] 27+ messages in thread

* Re: [PATCH v4 07/10] powerpc/mm: Use generic_hugetlb_get_unmapped_area()
  2021-12-16 17:13     ` Christophe Leroy
@ 2021-12-16 18:55       ` Catalin Marinas
  0 siblings, 0 replies; 27+ messages in thread
From: Catalin Marinas @ 2021-12-16 18:55 UTC (permalink / raw)
  To: Christophe Leroy
  Cc: Nicholas Piggin, alex, Benjamin Herrenschmidt, Michael Ellerman,
	Paul Mackerras, Will Deacon, Steve Capper, akpm, linux-kernel,
	linux-mm, linuxppc-dev, Linux ARM

On Thu, Dec 16, 2021 at 05:13:47PM +0000, Christophe Leroy wrote:
> Le 09/12/2021 à 11:02, Nicholas Piggin a écrit :
> > Excerpts from Christophe Leroy's message of December 9, 2021 3:18 am:
> >> Use the generic version of arch_hugetlb_get_unmapped_area()
> >> which is now available at all time.
> >>
> >> Signed-off-by: Christophe Leroy <christophe.leroy@csgroup.eu>
> >> ---
> >>   arch/powerpc/include/asm/book3s/64/hugetlb.h |  4 --
> >>   arch/powerpc/mm/book3s64/radix_hugetlbpage.c | 55 --------------------
> >>   arch/powerpc/mm/hugetlbpage.c                |  4 +-
> >>   3 files changed, 1 insertion(+), 62 deletions(-)
> >>
> >> diff --git a/arch/powerpc/include/asm/book3s/64/hugetlb.h b/arch/powerpc/include/asm/book3s/64/hugetlb.h
> >> index 12e150e615b7..b37a28f62cf6 100644
> >> --- a/arch/powerpc/include/asm/book3s/64/hugetlb.h
> >> +++ b/arch/powerpc/include/asm/book3s/64/hugetlb.h
> >> @@ -8,10 +8,6 @@
> >>    */
> >>   void radix__flush_hugetlb_page(struct vm_area_struct *vma, unsigned long vmaddr);
> >>   void radix__local_flush_hugetlb_page(struct vm_area_struct *vma, unsigned long vmaddr);
> >> -extern unsigned long
> >> -radix__hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
> >> -				unsigned long len, unsigned long pgoff,
> >> -				unsigned long flags);
> >>   
> >>   extern void radix__huge_ptep_modify_prot_commit(struct vm_area_struct *vma,
> >>   						unsigned long addr, pte_t *ptep,
> >> diff --git a/arch/powerpc/mm/book3s64/radix_hugetlbpage.c b/arch/powerpc/mm/book3s64/radix_hugetlbpage.c
> >> index 23d3e08911d3..d2fb776febb4 100644
> >> --- a/arch/powerpc/mm/book3s64/radix_hugetlbpage.c
> >> +++ b/arch/powerpc/mm/book3s64/radix_hugetlbpage.c
> >> @@ -41,61 +41,6 @@ void radix__flush_hugetlb_tlb_range(struct vm_area_struct *vma, unsigned long st
> >>   		radix__flush_tlb_range_psize(vma->vm_mm, start, end, psize);
> >>   }
> >>   
> >> -/*
> >> - * A vairant of hugetlb_get_unmapped_area doing topdown search
> >> - * FIXME!! should we do as x86 does or non hugetlb area does ?
> >> - * ie, use topdown or not based on mmap_is_legacy check ?
> >> - */
> >> -unsigned long
> >> -radix__hugetlb_get_unmapped_area(struct file *file, unsigned long addr,
> >> -				unsigned long len, unsigned long pgoff,
> >> -				unsigned long flags)
> >> -{
> >> -	struct mm_struct *mm = current->mm;
> >> -	struct vm_area_struct *vma;
> >> -	struct hstate *h = hstate_file(file);
> >> -	int fixed = (flags & MAP_FIXED);
> >> -	unsigned long high_limit;
> >> -	struct vm_unmapped_area_info info;
> >> -
> >> -	high_limit = DEFAULT_MAP_WINDOW;
> >> -	if (addr >= high_limit || (fixed && (addr + len > high_limit)))
> >> -		high_limit = TASK_SIZE;
> > 
> > I wonder if generic hugetlb_get_unmapped_area needs to have the
> > arch_get_mmap_end() added.
> > 
> > arm64 has arch_get_mmap_end() and !HAVE_ARCH_HUGETLB_UNMAPPED_AREA so
> > it looks like it has broken large address hint logic for hugetlbfs
> > mappings? x86-64 defines their own and does the same hinting for
> > normal and hugetlbfs mmap.
> > 
> > If we had that and defied arch_get_mmap_end(), then this patch should
> > work.
> > 
> 
> As far as I can see, hugetlb_get_unmapped_area() variants used to be 
> very similar to get_unmapped_area() until commit 1be7107fbe18 ("mm: 
> larger stack guard gap, between vmas") and commit f6795053dac8 ("mm: 
> mmap: Allow for "high" userspace addresses")
> 
> I see no reason why those changes couldn't apply to 
> hugetlb_get_unmapped_area() as well.
> 
> Need to know what ARM64 think about it thought. Will, Catalin, any opinion ?

I think we should have fixed hugetlb_get_unmapped_area() as well when we
added support for 52-bit VA. The reason for commit f6795053dac8 was to
prevent normal mmap() from returning addresses above 48-bit by default
as some user-space had hard assumptions about this.

It's a slight ABI change if you do this for hugetlb_get_unmapped_area()
but I doubt anyone would notice. It's more likely that the current
behaviour would cause issues, so I'd rather have them consistent.

-- 
Catalin

^ permalink raw reply	[flat|nested] 27+ messages in thread

end of thread, other threads:[~2021-12-16 18:55 UTC | newest]

Thread overview: 27+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-12-08 17:18 [PATCH v4 00/10] Convert powerpc to default topdown mmap layout Christophe Leroy
2021-12-08 17:18 ` [PATCH v4 01/10] mm: Allow arch specific arch_randomize_brk() with CONFIG_ARCH_WANT_DEFAULT_TOPDOWN_MMAP_LAYOUT Christophe Leroy
2021-12-08 17:18 ` [PATCH v4 02/10] mm, hugetlbfs: Allow an arch to always use generic versions of get_unmapped_area functions Christophe Leroy
2021-12-09  9:40   ` Nicholas Piggin
2021-12-08 17:18 ` [PATCH v4 03/10] powerpc/mm: Move vma_mmu_pagesize() Christophe Leroy
2021-12-09  9:36   ` Nicholas Piggin
2021-12-08 17:18 ` [PATCH v4 05/10] powerpc/mm: Remove CONFIG_PPC_MM_SLICES Christophe Leroy
2021-12-08 17:18 ` [PATCH v4 04/10] powerpc/mm: Make slice specific to book3s/64 Christophe Leroy
2021-12-08 17:18 ` [PATCH v4 06/10] powerpc/mm: Use generic_get_unmapped_area() and call it from arch_get_unmapped_area() Christophe Leroy
2021-12-09  9:50   ` Nicholas Piggin
2021-12-10 17:47     ` Christophe Leroy
2021-12-16 14:25     ` Christophe Leroy
2021-12-13 13:02   ` Michael Ellerman
2021-12-08 17:18 ` [PATCH v4 08/10] powerpc/mm: Move get_unmapped_area functions to slice.c Christophe Leroy
2021-12-08 17:18 ` [PATCH v4 07/10] powerpc/mm: Use generic_hugetlb_get_unmapped_area() Christophe Leroy
2021-12-09 10:02   ` Nicholas Piggin
2021-12-16 17:13     ` Christophe Leroy
2021-12-16 18:55       ` Catalin Marinas
2021-12-08 17:18 ` [PATCH v4 09/10] powerpc/mm: Convert to default topdown mmap layout Christophe Leroy
2021-12-09 10:15   ` Nicholas Piggin
2021-12-09 10:22     ` Christophe Leroy
2021-12-09 10:43       ` Nicholas Piggin
2021-12-09 11:22         ` Michael Ellerman
2021-12-09 11:32           ` Christophe Leroy
2021-12-09 23:56             ` Michael Ellerman
2021-12-16 14:27     ` Christophe Leroy
2021-12-08 17:18 ` [PATCH v4 10/10] powerpc/mm: Properly randomise mmap with slices Christophe Leroy

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).