From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from smtp.kernel.org (aws-us-west-2-korg-mail-1.web.codeaurora.org [10.30.226.201]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 82CD23B9D84; Fri, 15 May 2026 16:11:46 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=10.30.226.201 ARC-Seal:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1778861506; cv=none; b=JUaxUPgj0j3VtfmT6dbdZoKpVfQb8fSKeAILhE92TOi2OMrgIQxwTDyPudhmiFri7a9VFGL9gLMPj7qyyRiDctgQzhvhfVFN2AWCTYtGmIwJiXm+ewcTpQWhvOaaoq1yjE2ObyULsw2g+492FJE+fJGRpJpuPSN+pY4ubU6ewkk= ARC-Message-Signature:i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1778861506; c=relaxed/simple; bh=ZUO9Now5kGZXC7KYFpLjQEAFJoTq1zSFk5NgFH6U7Pg=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=CrR7qmH1iIPWl5E1Uxa0+4/VBsvDFqftpIInVP0T1zul7ogy3FA/DLRjzZbzbjjx4RvtY3IHjSKNZs73pMjKX7zAyQhi2I62O+bxe2et1//9n6/8aGiTB/kGTUhLVOqkRWL9mF1OUfAycu6VpXuM/gkg0kzKrIl0oqoVK8ij0l4= ARC-Authentication-Results:i=1; smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=linuxfoundation.org header.i=@linuxfoundation.org header.b=IV3jsSkN; arc=none smtp.client-ip=10.30.226.201 Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=linuxfoundation.org header.i=@linuxfoundation.org header.b="IV3jsSkN" Received: by smtp.kernel.org (Postfix) with ESMTPSA id 0D30EC2BCB0; Fri, 15 May 2026 16:11:45 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=linuxfoundation.org; s=korg; t=1778861506; bh=ZUO9Now5kGZXC7KYFpLjQEAFJoTq1zSFk5NgFH6U7Pg=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=IV3jsSkNjJAsqSd1SGT4ov1nLvDb2omax9XDPxIFfmKzVZAM7Tk4m8v2KG+CCS9wN ATXBXd6cOUST9TmugDu0cZVc7lWNEqUmMbtAWtHW2zSvT1vXg+VliMH/Y4hdki8C91 CpifqIPfLPavCnt7iEonhu6PRqPVJCG18AmEnMwY= From: Greg Kroah-Hartman To: stable@vger.kernel.org Cc: Greg Kroah-Hartman , patches@lists.linux.dev, Ben Morris , Xin Long , Jakub Kicinski Subject: [PATCH 6.6 355/474] sctp: revalidate list cursor after sctp_sendmsg_to_asoc() in SCTP_SENDALL Date: Fri, 15 May 2026 17:47:44 +0200 Message-ID: <20260515154722.699279668@linuxfoundation.org> X-Mailer: git-send-email 2.54.0 In-Reply-To: <20260515154715.053014143@linuxfoundation.org> References: <20260515154715.053014143@linuxfoundation.org> User-Agent: quilt/0.69 X-stable: review X-Patchwork-Hint: ignore Precedence: bulk X-Mailing-List: stable@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: 8bit 6.6-stable review patch. If anyone has any objections, please let me know. ------------------ From: Ben Morris commit abb5f36771cc4c05899b34000829a787572a8817 upstream. The SCTP_SENDALL path in sctp_sendmsg() iterates ep->asocs with list_for_each_entry_safe(), which caches the next entry in @tmp before the loop body runs. The body calls sctp_sendmsg_to_asoc(), which may drop the socket lock inside sctp_wait_for_sndbuf(). While the lock is dropped, another thread can SCTP_SOCKOPT_PEELOFF the association cached in @tmp, migrating it to a new endpoint via sctp_sock_migrate() (list_del_init() + list_add_tail() to newep->asocs), and optionally close the new socket which frees the association via kfree_rcu(). The cached @tmp can also be freed by a network ABORT for that association, processed in softirq while the lock is dropped. sctp_wait_for_sndbuf() revalidates @asoc (the current entry) on re-lock via the "sk != asoc->base.sk" and "asoc->base.dead" checks, but nothing revalidates @tmp. After a successful return, the iterator advances to the stale @tmp, yielding either a use-after-free (if the peeled socket was closed) or a list-walk onto the new endpoint's list head (type confusion of &newep->asocs as a struct sctp_association *). Both are reachable from CapEff=0; the type-confusion path gives controlled indirect call via the outqueue.sched->init_sid pointer. Fix by re-deriving @tmp from @asoc after sctp_sendmsg_to_asoc() returns. @asoc is known to still be on ep->asocs at that point: the only callers that list_del an association from ep->asocs are sctp_association_free() (which sets asoc->base.dead) and sctp_assoc_migrate() (which changes asoc->base.sk), and sctp_wait_for_sndbuf() checks both under the lock before any successful return; a tripped check propagates as err < 0 and the loop bails before the re-derive. The SCTP_ABORT path in sctp_sendmsg_check_sflags() returns 0 and the loop hits 'continue' before sctp_sendmsg_to_asoc() is ever called, so the @tmp cached by list_for_each_entry_safe() still covers the lock-held free that ba59fb027307 ("sctp: walk the list of asoc safely") was added for. Fixes: 4910280503f3 ("sctp: add support for snd flag SCTP_SENDALL process in sendmsg") Cc: stable@vger.kernel.org Signed-off-by: Ben Morris Acked-by: Xin Long Link: https://patch.msgid.link/20260508001455.3137-1-joycathacker@gmail.com Signed-off-by: Jakub Kicinski Signed-off-by: Greg Kroah-Hartman --- net/sctp/socket.c | 9 +++++++++ 1 file changed, 9 insertions(+) --- a/net/sctp/socket.c +++ b/net/sctp/socket.c @@ -1985,6 +1985,15 @@ static int sctp_sendmsg(struct sock *sk, goto out_unlock; iov_iter_revert(&msg->msg_iter, err); + + /* sctp_sendmsg_to_asoc() may have released the socket + * lock (sctp_wait_for_sndbuf), during which other + * associations on ep->asocs could have been peeled + * off or freed. @asoc itself is revalidated by the + * base.dead and base.sk checks in sctp_wait_for_sndbuf, + * so re-derive the cached cursor from it. + */ + tmp = list_next_entry(asoc, asocs); } goto out_unlock;