stable.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
To: linux-kernel@vger.kernel.org
Cc: Greg Kroah-Hartman <gregkh@linuxfoundation.org>,
	stable@vger.kernel.org, Andrea Arcangeli <aarcange@redhat.com>,
	zhong jiang <zhongjiang@huawei.com>,
	syzbot+cbb52e396df3e565ab02@syzkaller.appspotmail.com,
	Oleg Nesterov <oleg@redhat.com>, Jann Horn <jannh@google.com>,
	Hugh Dickins <hughd@google.com>,
	Mike Rapoport <rppt@linux.vnet.ibm.com>,
	Mike Kravetz <mike.kravetz@oracle.com>,
	Peter Xu <peterx@redhat.com>, Jason Gunthorpe <jgg@mellanox.com>,
	"Kirill A . Shutemov" <kirill.shutemov@linux.intel.com>,
	Michal Hocko <mhocko@suse.com>,
	Andrew Morton <akpm@linux-foundation.org>,
	Linus Torvalds <torvalds@linux-foundation.org>
Subject: [PATCH 4.14 34/63] userfaultfd: use RCU to free the task struct when fork fails
Date: Mon, 20 May 2019 14:14:13 +0200	[thread overview]
Message-ID: <20190520115235.088185357@linuxfoundation.org> (raw)
In-Reply-To: <20190520115231.137981521@linuxfoundation.org>

From: Andrea Arcangeli <aarcange@redhat.com>

commit c3f3ce049f7d97cc7ec9c01cb51d9ec74e0f37c2 upstream.

The task structure is freed while get_mem_cgroup_from_mm() holds
rcu_read_lock() and dereferences mm->owner.

  get_mem_cgroup_from_mm()                failing fork()
  ----                                    ---
  task = mm->owner
                                          mm->owner = NULL;
                                          free(task)
  if (task) *task; /* use after free */

The fix consists in freeing the task with RCU also in the fork failure
case, exactly like it always happens for the regular exit(2) path.  That
is enough to make the rcu_read_lock hold in get_mem_cgroup_from_mm()
(left side above) effective to avoid a use after free when dereferencing
the task structure.

An alternate possible fix would be to defer the delivery of the
userfaultfd contexts to the monitor until after fork() is guaranteed to
succeed.  Such a change would require more changes because it would
create a strict ordering dependency where the uffd methods would need to
be called beyond the last potentially failing branch in order to be
safe.  This solution as opposed only adds the dependency to common code
to set mm->owner to NULL and to free the task struct that was pointed by
mm->owner with RCU, if fork ends up failing.  The userfaultfd methods
can still be called anywhere during the fork runtime and the monitor
will keep discarding orphaned "mm" coming from failed forks in userland.

This race condition couldn't trigger if CONFIG_MEMCG was set =n at build
time.

[aarcange@redhat.com: improve changelog, reduce #ifdefs per Michal]
  Link: http://lkml.kernel.org/r/20190429035752.4508-1-aarcange@redhat.com
Link: http://lkml.kernel.org/r/20190325225636.11635-2-aarcange@redhat.com
Fixes: 893e26e61d04 ("userfaultfd: non-cooperative: Add fork() event")
Signed-off-by: Andrea Arcangeli <aarcange@redhat.com>
Tested-by: zhong jiang <zhongjiang@huawei.com>
Reported-by: syzbot+cbb52e396df3e565ab02@syzkaller.appspotmail.com
Cc: Oleg Nesterov <oleg@redhat.com>
Cc: Jann Horn <jannh@google.com>
Cc: Hugh Dickins <hughd@google.com>
Cc: Mike Rapoport <rppt@linux.vnet.ibm.com>
Cc: Mike Kravetz <mike.kravetz@oracle.com>
Cc: Peter Xu <peterx@redhat.com>
Cc: Jason Gunthorpe <jgg@mellanox.com>
Cc: "Kirill A . Shutemov" <kirill.shutemov@linux.intel.com>
Cc: Michal Hocko <mhocko@suse.com>
Cc: zhong jiang <zhongjiang@huawei.com>
Cc: syzbot+cbb52e396df3e565ab02@syzkaller.appspotmail.com
Cc: <stable@vger.kernel.org>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>

---
 kernel/fork.c |   31 +++++++++++++++++++++++++++++--
 1 file changed, 29 insertions(+), 2 deletions(-)

--- a/kernel/fork.c
+++ b/kernel/fork.c
@@ -790,6 +790,15 @@ static void mm_init_aio(struct mm_struct
 #endif
 }
 
+static __always_inline void mm_clear_owner(struct mm_struct *mm,
+					   struct task_struct *p)
+{
+#ifdef CONFIG_MEMCG
+	if (mm->owner == p)
+		WRITE_ONCE(mm->owner, NULL);
+#endif
+}
+
 static void mm_init_owner(struct mm_struct *mm, struct task_struct *p)
 {
 #ifdef CONFIG_MEMCG
@@ -1211,6 +1220,7 @@ static struct mm_struct *dup_mm(struct t
 free_pt:
 	/* don't put binfmt in mmput, we haven't got module yet */
 	mm->binfmt = NULL;
+	mm_init_owner(mm, NULL);
 	mmput(mm);
 
 fail_nomem:
@@ -1528,6 +1538,21 @@ static inline void rcu_copy_process(stru
 #endif /* #ifdef CONFIG_TASKS_RCU */
 }
 
+static void __delayed_free_task(struct rcu_head *rhp)
+{
+	struct task_struct *tsk = container_of(rhp, struct task_struct, rcu);
+
+	free_task(tsk);
+}
+
+static __always_inline void delayed_free_task(struct task_struct *tsk)
+{
+	if (IS_ENABLED(CONFIG_MEMCG))
+		call_rcu(&tsk->rcu, __delayed_free_task);
+	else
+		free_task(tsk);
+}
+
 /*
  * This creates a new process as a copy of the old one,
  * but does not actually start it yet.
@@ -1960,8 +1985,10 @@ bad_fork_cleanup_io:
 bad_fork_cleanup_namespaces:
 	exit_task_namespaces(p);
 bad_fork_cleanup_mm:
-	if (p->mm)
+	if (p->mm) {
+		mm_clear_owner(p->mm, p);
 		mmput(p->mm);
+	}
 bad_fork_cleanup_signal:
 	if (!(clone_flags & CLONE_THREAD))
 		free_signal_struct(p->signal);
@@ -1992,7 +2019,7 @@ bad_fork_cleanup_count:
 bad_fork_free:
 	p->state = TASK_DEAD;
 	put_task_stack(p);
-	free_task(p);
+	delayed_free_task(p);
 fork_out:
 	return ERR_PTR(retval);
 }



  parent reply	other threads:[~2019-05-20 12:19 UTC|newest]

Thread overview: 68+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2019-05-20 12:13 [PATCH 4.14 00/63] 4.14.121-stable review Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 01/63] net: core: another layer of lists, around PF_MEMALLOC skb handling Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 02/63] locking/rwsem: Prevent decrement of reader count before increment Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 03/63] PCI: hv: Fix a memory leak in hv_eject_device_work() Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 04/63] PCI: hv: Add hv_pci_remove_slots() when we unload the driver Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 05/63] PCI: hv: Add pci_destroy_slot() in pci_devices_present_work(), if necessary Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 06/63] x86/speculation/mds: Revert CPU buffer clear on double fault exit Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 07/63] x86/speculation/mds: Improve CPU buffer clear documentation Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 08/63] objtool: Fix function fallthrough detection Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 09/63] ARM: dts: exynos: Fix interrupt for shared EINTs on Exynos5260 Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 10/63] ARM: dts: exynos: Fix audio (microphone) routing on Odroid XU3 Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 11/63] ARM: exynos: Fix a leaked reference by adding missing of_node_put Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 12/63] power: supply: axp288_charger: Fix unchecked return value Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 13/63] arm64: compat: Reduce address limit Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 14/63] arm64: Clear OSDLR_EL1 on CPU boot Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 15/63] arm64: Save and restore OSDLR_EL1 across suspend/resume Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 16/63] sched/x86: Save [ER]FLAGS on context switch Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 17/63] crypto: chacha20poly1305 - set cra_name correctly Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 18/63] crypto: vmx - fix copy-paste error in CTR mode Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 19/63] crypto: skcipher - dont WARN on unprocessed data after slow walk step Greg Kroah-Hartman
2019-05-20 12:13 ` [PATCH 4.14 20/63] crypto: crct10dif-generic - fix use via crypto_shash_digest() Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 21/63] crypto: x86/crct10dif-pcl " Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 22/63] crypto: gcm - fix incompatibility between "gcm" and "gcm_base" Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 23/63] crypto: rockchip - update IV buffer to contain the next IV Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 24/63] crypto: arm/aes-neonbs - dont access already-freed walk.iv Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 25/63] ALSA: usb-audio: Fix a memory leak bug Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 26/63] ALSA: hda/hdmi - Read the pin sense from register when repolling Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 27/63] ALSA: hda/hdmi - Consider eld_valid when reporting jack event Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 28/63] ALSA: hda/realtek - EAPD turn on later Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 29/63] ASoC: max98090: Fix restore of DAPM Muxes Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 30/63] ASoC: RT5677-SPI: Disable 16Bit SPI Transfers Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 31/63] bpf, arm64: remove prefetch insn in xadd mapping Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 32/63] mm/mincore.c: make mincore() more conservative Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 33/63] ocfs2: fix ocfs2 read inode data panic in ocfs2_iget Greg Kroah-Hartman
2019-05-20 12:14 ` Greg Kroah-Hartman [this message]
2019-05-20 12:14 ` [PATCH 4.14 35/63] mfd: da9063: Fix OTP control register names to match datasheets for DA9063/63L Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 36/63] mfd: max77620: Fix swapped FPS_PERIOD_MAX_US values Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 37/63] mtd: spi-nor: intel-spi: Avoid crossing 4K address boundary on read/write Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 38/63] tty: vt.c: Fix TIOCL_BLANKSCREEN console blanking if blankinterval == 0 Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 39/63] tty/vt: fix write/write race in ioctl(KDSKBSENT) handler Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 40/63] jbd2: check superblock mapped prior to committing Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 41/63] ext4: make sanity check in mballoc more strict Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 42/63] ext4: ignore e_value_offs for xattrs with value-in-ea-inode Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 43/63] ext4: avoid drop reference to iloc.bh twice Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 44/63] Btrfs: do not start a transaction during fiemap Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 45/63] Btrfs: do not start a transaction at iterate_extent_inodes() Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 46/63] bcache: fix a race between cache register and cacheset unregister Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 47/63] bcache: never set KEY_PTRS of journal key to 0 in journal_reclaim() Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 48/63] ext4: fix use-after-free race with debug_want_extra_isize Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 49/63] ext4: actually request zeroing of inode table after grow Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 50/63] ext4: fix ext4_show_options for file systems w/o journal Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 51/63] ipmi:ssif: compare block number correctly for multi-part return messages Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 52/63] crypto: arm64/aes-neonbs - dont access already-freed walk.iv Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 53/63] crypto: salsa20 " Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 54/63] crypto: ccm - fix incompatibility between "ccm" and "ccm_base" Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 55/63] fib_rules: fix error in backport of e9919a24d302 ("fib_rules: return 0...") Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 56/63] fs/writeback.c: use rcu_barrier() to wait for inflight wb switches going into workqueue when umount Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 57/63] ext4: zero out the unused memory region in the extent tree block Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 58/63] ext4: fix data corruption caused by overlapping unaligned and aligned IO Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 59/63] ext4: fix use-after-free in dx_release() Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 60/63] ALSA: hda/realtek - Fix for Lenovo B50-70 inverted internal microphone bug Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 61/63] KVM: x86: Skip EFER vs. guest CPUID checks for host-initiated writes Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 62/63] iov_iter: optimize page_copy_sane() Greg Kroah-Hartman
2019-05-20 12:14 ` [PATCH 4.14 63/63] ext4: fix compile error when using BUFFER_TRACE Greg Kroah-Hartman
2019-05-20 18:28 ` [PATCH 4.14 00/63] 4.14.121-stable review kernelci.org bot
2019-05-21  8:51 ` Jon Hunter
2019-05-21 10:38 ` Naresh Kamboju
2019-05-21 21:35 ` shuah

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=20190520115235.088185357@linuxfoundation.org \
    --to=gregkh@linuxfoundation.org \
    --cc=aarcange@redhat.com \
    --cc=akpm@linux-foundation.org \
    --cc=hughd@google.com \
    --cc=jannh@google.com \
    --cc=jgg@mellanox.com \
    --cc=kirill.shutemov@linux.intel.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=mhocko@suse.com \
    --cc=mike.kravetz@oracle.com \
    --cc=oleg@redhat.com \
    --cc=peterx@redhat.com \
    --cc=rppt@linux.vnet.ibm.com \
    --cc=stable@vger.kernel.org \
    --cc=syzbot+cbb52e396df3e565ab02@syzkaller.appspotmail.com \
    --cc=torvalds@linux-foundation.org \
    --cc=zhongjiang@huawei.com \
    /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 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).