From mboxrd@z Thu Jan 1 00:00:00 1970 Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.remote-ip=100.103.45.18 ARC-Seal: i=1; d=subspace.kernel.org; s=arc20261015; a=rsa-sha256; cv=none; t=1792773919; b=FU4ZvSkR6mn3xU5xxfpK5W8aroUM0wdZlszFVsVJYVPG4mGJSmdyAIvUMSsQbhfbpu9f iJia00UXJ/FrKZ2o/zSpONdzHHOHGT3Oosi248hVC37oNoAiZQ7h5gVrrjYe2U+mKSCP2 g8nnwNTgM1xep/xi+TizZWzyoIX7my+46142WV4rjDUHAX4hagDcnaHFpyUv9JKW/Ph6a vafBOybdGbyZcGuy/5BUxifUyDYXRddEPhxi9y0GLqsmnotqqhju7tHHyrerBMOK0hMPa wv7PP+7kS8JkuJjfMVHWk08MdZb7MmPFhg5cEbQH1s2FRSY2OdS5eLFMfxe9dxD2ymA== ARC-Message-Signature: i=1; d=subspace.kernel.org; s=arc20261015; a=rsa-sha256; c=relaxed/relaxed; t=1792773919; h=Received:DKIM-Signature:From:To:Cc:Subject:Date:Message-ID:X-Mailer: In-Reply-To:References:User-Agent:X-stable:X-Patchwork-Hint: MIME-Version:Content-Transfer-Encoding; bh=bZ9RV2PG8qTKMkuTk85Jnp1Q/HUzEMkHobfqDVGCVXw=; b=jED1YmavFQqOlRepFYyZNQuJQoTKSspx+YrDrJfxn0H1x1vkGm4r2m2s6u6qKo+O4Dwo kTyJfT92YzxPWtwTxoaUck9N494l0oTBGVB4xC2FzSZ+2S2EfXB/sL9VKQ863xDqYEnAd M4KtP/MvpcUkYvlfZBlhEJx+BSNueRjmykbr/vB/XQKu3q/KG2b0LBJ0gdpic7dME1/Uz qt2yIeQvHbsRxx3NhVL3Sn6LK9sYN/dbPogb5XthYIGEqxejpuj++vCX3xRKIYkCECvik Rj+OKcLDpubUP8ZjAzVfXq4if5Z6SbmdC0KERY+YM/K72u4L2KKF2msZrQrs5J5v50w== ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dkim=pass header.d=linuxfoundation.org header.i=@linuxfoundation.org header.a=rsa-sha256 header.s=korg header.b="ZGeG+oW/"; arc=none smtp.remote-ip=100.103.45.18 Received: from smtp.kernel.org (quasi.space.kernel.org [100.103.45.18]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (prime256v1)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 56012606A320; Fri, 23 Oct 2026 16:45:19 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key, unprotected) header.d=linuxfoundation.org header.i=@linuxfoundation.org header.a=rsa-sha256 header.s=korg header.b=ZGeG+oW/ Received: by smtp.kernel.org (Postfix) with ESMTPSA id A108D1F01829; Fri, 23 Oct 2026 16:45:18 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linuxfoundation.org; s=korg; t=1792773919; bh=bZ9RV2PG8qTKMkuTk85Jnp1Q/HUzEMkHobfqDVGCVXw=; h=From:To:Cc:Subject:Date:In-Reply-To:References; b=ZGeG+oW/Z+fn+F6ZeM7Bi28gElm+h3qJ6WdHWXcfvXwkrSXlMrdReDBk+o8dtF/re AqokIKu3vzGb114ZtmXpaKQhPB7LKBHyCcaSfSE60SGwvy9siIj4k9gzDmC9z9Qf6w DkpgnSDKdeQ0L9tlSdPR9Nsf8Ss7GcrBzjACYjSM= From: Greg Kroah-Hartman To: stable@vger.kernel.org Cc: Greg Kroah-Hartman , patches@lists.linux.dev, Cen Zhang , Joseph Qi , "Christian Brauner (Amutable)" , Sasha Levin Subject: [PATCH 6.18 053/193] ocfs2/dlm: Protect the recovery list during debugfs reads Date: Fri, 23 Oct 2026 18:35:30 +0200 Message-ID: <20261023163715.460370267@linuxfoundation.org> X-Mailer: git-send-email 2.56.0 In-Reply-To: <20261023163714.201276352@linuxfoundation.org> References: <20261023163714.201276352@linuxfoundation.org> User-Agent: quilt/0.69 X-stable: review X-Patchwork-Hint: ignore X-Mailing-List: patches@lists.linux.dev List-Id: List-Post: List-Help: List-Subscribe: List-Unsubscribe: List-Owner: Precedence: list MIME-Version: 1.0 Content-Transfer-Encoding: 8bit 6.18-stable review patch. If anyone has any objections, please let me know. ------------------ From: Cen Zhang [ Upstream commit 4c435828932bf46f29860e4a0375bcae101b778a ] Recovery participant records must remain alive while debug_state_print() walks reco.node_data and formats their fields. The formatter holds dlm->spinlock, but the recovery participant list is protected by dlm_reco_state_lock. In particular, dlm_destroy_recovery_area() detaches the list under dlm_reco_state_lock and frees the detached records after releasing it. A concurrent debugfs open can therefore read freed memory. Protect the participant traversal and field reads in debug_state_print() with dlm_reco_state_lock, matching the existing list writers. This also serializes the traversal against list_add_tail() during recovery-area initialization. Make the existing lock available to the debug code through dlmcommon.h; the lock remains internal to the OCFS2 DLM module. Release dlm->spinlock after formatting the other domain state and before acquiring dlm_reco_state_lock, so the debug reader does not nest the two locks. Leave recovery list insertion, detachment and freeing unchanged. KASAN report as below: BUG: KASAN: slab-use-after-free in debug_state_open+0x1169/0x12d0 Read of size 4 at addr ffff88810662ef80 by task dlm-state-stres/896 CPU: 1 UID: 0 PID: 896 Comm: dlm-state-stres Not tainted 7.3.0-rc4-next-20260921-pmb-ocfs2-functional-v1+ #1 PREEMPT(lazy) Hardware name: QEMU Ubuntu 24.04 PC v2 (i440FX + PIIX, arch_caps fix, 1996), BIOS 1.16.3-debian-1.16.3-2 04/01/2014 Call Trace: dump_stack_lvl+0x93/0xd0 print_report+0xce/0x630 ? debug_state_open+0x1169/0x12d0 ? srso_alias_return_thunk+0x5/0xfbef5 ? __virt_addr_valid+0x20e/0x420 ? debug_state_open+0x1169/0x12d0 kasan_report+0xe0/0x110 ? debug_state_open+0x1169/0x12d0 debug_state_open+0x1169/0x12d0 ? __pfx_debug_state_open+0x10/0x10 full_proxy_open_regular+0x193/0x310 do_dentry_open+0x595/0x12d0 ? __pfx_full_proxy_open_regular+0x10/0x10 vfs_open_consume+0xd1/0x400 ? srso_alias_return_thunk+0x5/0xfbef5 path_openat+0x18d0/0x2020 ? __pfx_path_openat+0x10/0x10 do_file_open+0x21e/0x470 ? __pfx_do_file_open+0x10/0x10 ? _raw_spin_unlock+0x23/0x40 ? srso_alias_return_thunk+0x5/0xfbef5 ? alloc_fd+0x3a6/0x6b0 do_sys_openat2+0xf4/0x1b0 ? __pfx_do_sys_openat2+0x10/0x10 ? srso_alias_return_thunk+0x5/0xfbef5 ? __fput+0x5b5/0xa60 __x64_sys_openat+0x136/0x1e0 ? __pfx___x64_sys_openat+0x10/0x10 do_syscall_64+0x114/0x620 entry_SYSCALL_64_after_hwframe+0x77/0x7f [Register dump omitted.] Allocated by task 880: kasan_save_stack+0x33/0x60 kasan_save_track+0x14/0x30 __kasan_kmalloc+0xaa/0xb0 __kmalloc_cache_noprof+0x28d/0x610 dlm_remaster_locks+0x147/0x1d90 dlm_do_recovery+0xde1/0x1580 dlm_recovery_thread+0x109/0x300 kthread+0x351/0x460 ret_from_fork+0x659/0x940 ret_from_fork_asm+0x1a/0x30 Freed by task 880: kasan_save_stack+0x33/0x60 kasan_save_track+0x14/0x30 kasan_save_free_info+0x3b/0x60 __kasan_slab_free+0x5f/0x80 kfree+0x308/0x580 dlm_destroy_recovery_area+0x285/0x460 dlm_remaster_locks+0x17c4/0x1d90 dlm_do_recovery+0xde1/0x1580 dlm_recovery_thread+0x109/0x300 kthread+0x351/0x460 ret_from_fork+0x659/0x940 ret_from_fork_asm+0x1a/0x30 The buggy address belongs to the object at ffff88810662ef80 which belongs to the cache kmalloc-32 of size 32 The buggy address is located 0 bytes inside of freed 32-byte region [ffff88810662ef80, ffff88810662efa0) [Page and memory-state dumps omitted.] Fixes: 007dce53a29c ("ocfs2/dlm: Dump the dlm state in a debugfs file") Signed-off-by: Cen Zhang Link: https://patch.msgid.link/pm-ocfs2-objects-candidate-0049-v3-184e46c47f5283f06191@gmail.com Reviewed-by: Joseph Qi Signed-off-by: Christian Brauner (Amutable) Signed-off-by: Sasha Levin --- fs/ocfs2/dlm/dlmcommon.h | 2 ++ fs/ocfs2/dlm/dlmdebug.c | 5 ++++- fs/ocfs2/dlm/dlmrecovery.c | 2 +- 3 files changed, 7 insertions(+), 2 deletions(-) diff --git a/fs/ocfs2/dlm/dlmcommon.h b/fs/ocfs2/dlm/dlmcommon.h index 20f790a47484a..58b28dfa8d34e 100644 --- a/fs/ocfs2/dlm/dlmcommon.h +++ b/fs/ocfs2/dlm/dlmcommon.h @@ -435,6 +435,8 @@ enum { DLM_DEREF_LOCKRES_DONE = 522, }; +extern spinlock_t dlm_reco_state_lock; + struct dlm_reco_node_data { int state; diff --git a/fs/ocfs2/dlm/dlmdebug.c b/fs/ocfs2/dlm/dlmdebug.c index 5645673586201..38a6a99603a9c 100644 --- a/fs/ocfs2/dlm/dlmdebug.c +++ b/fs/ocfs2/dlm/dlmdebug.c @@ -740,8 +740,11 @@ static int debug_state_print(struct dlm_ctxt *dlm, char *buf, int len) buf + out, len - out); out += scnprintf(buf + out, len - out, "\n"); + spin_unlock(&dlm->spinlock); + /* Recovery Node State: */ out += scnprintf(buf + out, len - out, "Recovery Node State:\n"); + spin_lock(&dlm_reco_state_lock); list_for_each_entry(node, &dlm->reco.node_data, list) { switch (node->state) { case DLM_RECO_NODE_DATA_INIT: @@ -773,7 +776,7 @@ static int debug_state_print(struct dlm_ctxt *dlm, char *buf, int len) node->node_num, state); } - spin_unlock(&dlm->spinlock); + spin_unlock(&dlm_reco_state_lock); return out; } diff --git a/fs/ocfs2/dlm/dlmrecovery.c b/fs/ocfs2/dlm/dlmrecovery.c index 2379225f0ee69..a55787282eaf0 100644 --- a/fs/ocfs2/dlm/dlmrecovery.c +++ b/fs/ocfs2/dlm/dlmrecovery.c @@ -80,7 +80,7 @@ static int dlm_lockres_master_requery(struct dlm_ctxt *dlm, static u64 dlm_get_next_mig_cookie(void); -static DEFINE_SPINLOCK(dlm_reco_state_lock); +DEFINE_SPINLOCK(dlm_reco_state_lock); static DEFINE_SPINLOCK(dlm_mig_cookie_lock); static u64 dlm_mig_cookie = 1; -- 2.53.0