Go to file
Jann Horn d8ab9f7b64 mm: lock VMA in dup_anon_vma() before setting ->anon_vma
When VMAs are merged, dup_anon_vma() is called with `dst` pointing to the
VMA that is being expanded to cover the area previously occupied by
another VMA.  This currently happens while `dst` is not write-locked.

This means that, in the `src->anon_vma && !dst->anon_vma` case, as soon as
the assignment `dst->anon_vma = src->anon_vma` has happened, concurrent
page faults can happen on `dst` under the per-VMA lock.  This is already
icky in itself, since such page faults can now install pages into `dst`
that are attached to an `anon_vma` that is not yet tied back to the
`anon_vma` with an `anon_vma_chain`.  But if `anon_vma_clone()` fails due
to an out-of-memory error, things get much worse: `anon_vma_clone()` then
reverts `dst->anon_vma` back to NULL, and `dst` remains completely
unconnected to the `anon_vma`, even though we can have pages in the area
covered by `dst` that point to the `anon_vma`.

This means the `anon_vma` of such pages can be freed while the pages are
still mapped into userspace, which leads to UAF when a helper like
folio_lock_anon_vma_read() tries to look up the anon_vma of such a page.

This theoretically is a security bug, but I believe it is really hard to
actually trigger as an unprivileged user because it requires that you can
make an order-0 GFP_KERNEL allocation fail, and the page allocator tries
pretty hard to prevent that.

I think doing the vma_start_write() call inside dup_anon_vma() is the most
straightforward fix for now.

For a kernel-assisted reproducer, see the notes section of the patch mail.

Link: https://lkml.kernel.org/r/20230721034643.616851-1-jannh@google.com
Fixes: 5e31275cc9 ("mm: add per-VMA lock and helper functions to control it")
Signed-off-by: Jann Horn <jannh@google.com>
Reviewed-by: Suren Baghdasaryan <surenb@google.com>
Cc: <stable@vger.kernel.org>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
2023-07-27 13:07:04 -07:00
Documentation tmpfs: fix Documentation of noswap and huge mount options 2023-07-27 13:07:03 -07:00
LICENSES
arch Revert "um: Use swap() to make code cleaner" 2023-07-27 13:07:03 -07:00
block block-6.5-2023-07-21 2023-07-22 11:05:15 -07:00
certs
crypto
drivers s390 fixes for 6.5-rc3 2023-07-22 11:24:03 -07:00
fs Bug and regression fixes for 6.5-rc3 for ext4's mballoc and jbd2's 2023-07-23 10:21:49 -07:00
include mm: fix memory ordering for mm_lock_seq and vm_lock_seq 2023-07-27 13:07:04 -07:00
init
io_uring io_uring-6.5-2023-07-21 2023-07-22 10:46:30 -07:00
ipc
kernel Tracing fixes for 6.5-rc2: 2023-07-23 15:19:14 -07:00
lib block-6.5-2023-07-21 2023-07-22 11:05:15 -07:00
mm mm: lock VMA in dup_anon_vma() before setting ->anon_vma 2023-07-27 13:07:04 -07:00
net Including fixes from BPF, netfilter, bluetooth and CAN. 2023-07-20 14:46:39 -07:00
rust
samples
scripts scripts/spelling.txt: remove 'thead' as a typo 2023-07-27 13:07:04 -07:00
security
sound
tools sound fixes for 6.5-rc3 2023-07-21 10:10:18 -07:00
usr
virt
.clang-format
.cocciconfig
.get_maintainer.ignore
.gitattributes
.gitignore
.mailmap Including fixes from BPF, netfilter, bluetooth and CAN. 2023-07-20 14:46:39 -07:00
.rustfmt.toml
COPYING
CREDITS
Kbuild
Kconfig
MAINTAINERS
Makefile Linux 6.5-rc3 2023-07-23 15:24:10 -07:00
README

README

Linux kernel
============

There are several guides for kernel developers and users. These guides can
be rendered in a number of formats, like HTML and PDF. Please read
Documentation/admin-guide/README.rst first.

In order to build the documentation, use ``make htmldocs`` or
``make pdfdocs``.  The formatted documentation can also be read online at:

    https://www.kernel.org/doc/html/latest/

There are various text files in the Documentation/ subdirectory,
several of them using the Restructured Text markup notation.

Please read the Documentation/process/changes.rst file, as it contains the
requirements for building and running the kernel, and information about
the problems which may result by upgrading your kernel.