All of lore.kernel.org
 help / color / mirror / Atom feed
From: Rick Edgecombe <rick.p.edgecombe@intel.com>
To: Liam.Howlett@oracle.com, akpm@linux-foundation.org, bp@alien8.de,
	broonie@kernel.org, dave.hansen@linux.intel.com,
	debug@rivosinc.com, hpa@zytor.com, keescook@chromium.org,
	kirill.shutemov@linux.intel.com, luto@kernel.org,
	mingo@redhat.com, peterz@infradead.org, tglx@linutronix.de,
	x86@kernel.org, christophe.leroy@csgroup.eu
Cc: linux-kernel@vger.kernel.org, linux-mm@kvack.org,
	rick.p.edgecombe@intel.com
Subject: [PATCH v3 09/12] mm: Take placement mappings gap into account
Date: Tue, 12 Mar 2024 15:28:40 -0700	[thread overview]
Message-ID: <20240312222843.2505560-10-rick.p.edgecombe@intel.com> (raw)
In-Reply-To: <20240312222843.2505560-1-rick.p.edgecombe@intel.com>

When memory is being placed, mmap() will take care to respect the guard
gaps of certain types of memory (VM_SHADOWSTACK, VM_GROWSUP and
VM_GROWSDOWN). In order to ensure guard gaps between mappings, mmap()
needs to consider two things:
 1. That the new mapping isn’t placed in an any existing mappings guard
    gaps.
 2. That the new mapping isn’t placed such that any existing mappings
    are not in *its* guard gaps.

The long standing behavior of mmap() is to ensure 1, but not take any care
around 2. So for example, if there is a PAGE_SIZE free area, and a
mmap() with a PAGE_SIZE size, and a type that has a guard gap is being
placed, mmap() may place the shadow stack in the PAGE_SIZE free area. Then
the mapping that is supposed to have a guard gap will not have a gap to
the adjacent VMA.

For MAP_GROWSDOWN/VM_GROWSDOWN and MAP_GROWSUP/VM_GROWSUP this has not
been a problem in practice because applications place these kinds of
mappings very early, when there is not many mappings to find a space
between. But for shadow stacks, they may be placed throughout the lifetime
of the application.

Use the start_gap field to find a space that includes the guard gap for
the new mapping. Take care to not interfere with the alignment.

Signed-off-by: Rick Edgecombe <rick.p.edgecombe@intel.com>
---
v3:
 - Spelling fix in comment

v2:
 - Remove VM_UNMAPPED_START_GAP_SET and have struct vm_unmapped_area_info
   initialized with zeros (in another patch). (Kirill)
 - Drop unrelated space change (Kirill)
 - Add comment around interactions of alignment and start gap step
   (Kirill)
---
 include/linux/mm.h |  1 +
 mm/mmap.c          | 12 +++++++++---
 2 files changed, 10 insertions(+), 3 deletions(-)

diff --git a/include/linux/mm.h b/include/linux/mm.h
index d91cde79aaee..deade7be00d0 100644
--- a/include/linux/mm.h
+++ b/include/linux/mm.h
@@ -3418,6 +3418,7 @@ struct vm_unmapped_area_info {
 	unsigned long high_limit;
 	unsigned long align_mask;
 	unsigned long align_offset;
+	unsigned long start_gap;
 };
 
 extern unsigned long vm_unmapped_area(struct vm_unmapped_area_info *info);
diff --git a/mm/mmap.c b/mm/mmap.c
index b889c79d11bd..634e706fd97e 100644
--- a/mm/mmap.c
+++ b/mm/mmap.c
@@ -1582,7 +1582,7 @@ static unsigned long unmapped_area(struct vm_unmapped_area_info *info)
 	MA_STATE(mas, &current->mm->mm_mt, 0, 0);
 
 	/* Adjust search length to account for worst case alignment overhead */
-	length = info->length + info->align_mask;
+	length = info->length + info->align_mask + info->start_gap;
 	if (length < info->length)
 		return -ENOMEM;
 
@@ -1594,7 +1594,13 @@ static unsigned long unmapped_area(struct vm_unmapped_area_info *info)
 	if (mas_empty_area(&mas, low_limit, high_limit - 1, length))
 		return -ENOMEM;
 
-	gap = mas.index;
+	/*
+	 * Adjust for the gap first so it doesn't interfere with the
+	 * later alignment. The first step is the minimum needed to
+	 * fulill the start gap, the next steps is the minimum to align
+	 * that. It is the minimum needed to fulill both.
+	 */
+	gap = mas.index + info->start_gap;
 	gap += (info->align_offset - gap) & info->align_mask;
 	tmp = mas_next(&mas, ULONG_MAX);
 	if (tmp && (tmp->vm_flags & VM_STARTGAP_FLAGS)) { /* Avoid prev check if possible */
@@ -1633,7 +1639,7 @@ static unsigned long unmapped_area_topdown(struct vm_unmapped_area_info *info)
 
 	MA_STATE(mas, &current->mm->mm_mt, 0, 0);
 	/* Adjust search length to account for worst case alignment overhead */
-	length = info->length + info->align_mask;
+	length = info->length + info->align_mask + info->start_gap;
 	if (length < info->length)
 		return -ENOMEM;
 
-- 
2.34.1


  parent reply	other threads:[~2024-03-12 22:29 UTC|newest]

Thread overview: 46+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2024-03-12 22:28 [PATCH v3 00/12] Cover a guard gap corner case Rick Edgecombe
2024-03-12 22:28 ` [PATCH v3 01/12] mm: Switch mm->get_unmapped_area() to a flag Rick Edgecombe
2024-03-13  7:19   ` Christophe Leroy
2024-03-13 14:48     ` Edgecombe, Rick P
2024-03-13 17:20       ` Christophe Leroy
2024-03-12 22:28 ` [PATCH v3 02/12] mm: Introduce arch_get_unmapped_area_vmflags() Rick Edgecombe
2024-03-13  7:22   ` Christophe Leroy
2024-03-13 14:51     ` Edgecombe, Rick P
2024-03-12 22:28 ` [PATCH v3 03/12] mm: Use get_unmapped_area_vmflags() Rick Edgecombe
2024-03-13  9:05   ` Christophe Leroy
2024-03-13 14:55     ` Edgecombe, Rick P
2024-03-13 16:49       ` Christophe Leroy
2024-03-13 15:55     ` Edgecombe, Rick P
2024-03-12 22:28 ` [PATCH v3 04/12] thp: Add thp_get_unmapped_area_vmflags() Rick Edgecombe
2024-03-13  9:04   ` Christophe Leroy
2024-03-12 22:28 ` [PATCH v3 05/12] csky: Use initializer for struct vm_unmapped_area_info Rick Edgecombe
2024-03-13  9:04   ` Christophe Leroy
2024-03-12 22:28 ` [PATCH v3 06/12] parisc: " Rick Edgecombe
2024-03-13  9:04   ` Christophe Leroy
2024-03-12 22:28 ` [PATCH v3 07/12] powerpc: " Rick Edgecombe
2024-03-12 22:28   ` Rick Edgecombe
2024-03-13  6:44   ` Christophe Leroy
2024-03-13  6:44     ` Christophe Leroy
2024-03-13 14:57     ` Edgecombe, Rick P
2024-03-13 14:57       ` Edgecombe, Rick P
2024-03-13 21:58       ` Michael Ellerman
2024-03-13 21:58         ` Michael Ellerman
2024-03-12 22:28 ` [PATCH v3 08/12] treewide: " Rick Edgecombe
2024-03-12 22:28   ` Rick Edgecombe
2024-03-12 22:28   ` Rick Edgecombe
2024-03-13  3:18   ` Kees Cook
2024-03-13  3:18     ` Kees Cook
2024-03-13  3:18     ` Kees Cook
2024-03-13 15:40     ` Edgecombe, Rick P
2024-03-13 15:40       ` Edgecombe, Rick P
2024-03-13 15:40       ` Edgecombe, Rick P
2024-03-12 22:28 ` Rick Edgecombe [this message]
2024-03-13  9:04   ` [PATCH v3 09/12] mm: Take placement mappings gap into account Christophe Leroy
2024-03-13 14:58     ` Edgecombe, Rick P
2024-03-13 16:51       ` Christophe Leroy
2024-03-12 22:28 ` [PATCH v3 10/12] x86/mm: Implement HAVE_ARCH_UNMAPPED_AREA_VMFLAGS Rick Edgecombe
2024-03-13  9:04   ` Christophe Leroy
2024-03-13 16:00     ` Edgecombe, Rick P
2024-03-18  1:00       ` Edgecombe, Rick P
2024-03-12 22:28 ` [PATCH v3 11/12] x86/mm: Care about shadow stack guard gap during placement Rick Edgecombe
2024-03-12 22:28 ` [PATCH v3 12/12] selftests/x86: Add placement guard gap test for shstk Rick Edgecombe

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20240312222843.2505560-10-rick.p.edgecombe@intel.com \
    --to=rick.p.edgecombe@intel.com \
    --cc=Liam.Howlett@oracle.com \
    --cc=akpm@linux-foundation.org \
    --cc=bp@alien8.de \
    --cc=broonie@kernel.org \
    --cc=christophe.leroy@csgroup.eu \
    --cc=dave.hansen@linux.intel.com \
    --cc=debug@rivosinc.com \
    --cc=hpa@zytor.com \
    --cc=keescook@chromium.org \
    --cc=kirill.shutemov@linux.intel.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-mm@kvack.org \
    --cc=luto@kernel.org \
    --cc=mingo@redhat.com \
    --cc=peterz@infradead.org \
    --cc=tglx@linutronix.de \
    --cc=x86@kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.