Netdev List
 help / color / mirror / Atom feed
From: Doruk Tan Ozturk <doruk@0sec.ai>
To: tung.quang.nguyen@est.tech
Cc: jmaloy@redhat.com, aleksander.lobakin@intel.com,
	davem@davemloft.net, edumazet@google.com, kuba@kernel.org,
	pabeni@redhat.com, horms@kernel.org, netdev@vger.kernel.org,
	tipc-discussion@lists.sourceforge.net,
	linux-kernel@vger.kernel.org
Subject: Re: [PATCH net v2] tipc: fix slab-use-after-free Read in tipc_aead_decrypt_done
Date: Mon, 15 Jun 2026 02:22:11 +0200	[thread overview]
Message-ID: <20260615002211.90694-1-doruk@0sec.ai> (raw)
In-Reply-To: <GV1P189MB1988B2B662DC781F7347EBD4C61B2@GV1P189MB1988.EURP189.PROD.OUTLOOK.COM>

On Tue, Jun 10, 2026, Tung Quang Nguyen wrote:
> Can you decode the stack trace (using linux/scripts/decode_stacktrace.sh)
> for more readable text?
>
> Is the issue reproducible on the latest net branch, or just on the old
> v6.12.92 you mentioned?

Hi Tung,

Thanks for the review. Answers to both questions below.

1) Decoded stack trace
----------------------
Decoded with scripts/decode_stacktrace.sh against the vmlinux that produced
the splat (6.12.92, CONFIG_KASAN_INLINE + CONFIG_TIPC + CONFIG_TIPC_CRYPTO).
The use-after-free read and the allocation/free sites resolve as follows:

BUG: KASAN: slab-use-after-free in tipc_crypto_rcv_complete (net/tipc/crypto.c:1917)
Read of size 8 at addr ffff888104c8c808 by task kworker/3:2/70
Workqueue: cryptd cryptd_queue_worker
Call Trace:
 <TASK>
 dump_stack_lvl (lib/dump_stack.c:123)
 print_report (mm/kasan/report.c:378 mm/kasan/report.c:481)
 kasan_report (mm/kasan/report.c:596)
 tipc_crypto_rcv_complete (net/tipc/crypto.c:1917)
 tipc_aead_decrypt_done (net/tipc/crypto.c:996)
 cryptd_aead_crypt (include/crypto/internal/aead.h:85 crypto/cryptd.c:772)
 cryptd_queue_worker (crypto/cryptd.c:181)
 process_one_work (kernel/workqueue.c:3264)
 worker_thread (kernel/workqueue.c:3339 kernel/workqueue.c:3426)
 kthread (kernel/kthread.c:389)
 ret_from_fork (arch/x86/kernel/process.c:152)
 ret_from_fork_asm (arch/x86/entry/entry_64.S:257)
 </TASK>

Allocated by task 1550:
 kasan_save_stack (mm/kasan/common.c:49)
 kasan_save_track (mm/kasan/common.c:61 mm/kasan/common.c:70)
 __kasan_kmalloc (mm/kasan/common.c:378 mm/kasan/common.c:395)
 tipc_crypto_start (net/tipc/crypto.c:1484)
 tipc_init_net (net/tipc/core.c:73)
 ops_init (net/core/net_namespace.c:140)
 setup_net (net/core/net_namespace.c:357)
 copy_net_ns (net/core/net_namespace.c:512)
 create_new_namespaces (kernel/nsproxy.c:110)

(The captured report has the KASAN read trace and the Allocated-by track; the
free is on the netns teardown path tipc_crypto_stop() <- tipc_exit_net() <-
cleanup_net(), as described in the changelog.)

So the freed object is the per-netns struct tipc_crypto allocated in
tipc_crypto_start() at netns creation (crypto.c:1484), and the cryptd worker
then reads it from the async completion: tipc_aead_decrypt_done()
(crypto.c:996) -> tipc_crypto_rcv_complete() (crypto.c:1917). Immediately after
the UAF read the worker also faults dereferencing the stale node pointer in
tipc_node_put() (net/tipc/node.c:319), confirming the object is gone.

2) Reproducibility on the latest net branch
--------------------------------------------
The bug is still present on the latest net tree. I checked out v7.1-rc7 and
inspected net/tipc/crypto.c first: the encrypt side already carries the
maybe_get_net() guard from commit e279024617134 ("net/tipc: fix
slab-use-after-free Read in tipc_aead_encrypt"), but tipc_aead_decrypt() still
goes straight from tipc_bearer_hold(b) to crypto_aead_decrypt(req) with no
maybe_get_net(aead->crypto->net) and no matching put_net() -- i.e. the exact
gap this patch closes. So the decrypt path is unguarded on 7.1-rc7 and the UAF
is reachable there in the same way.

I also built v7.1-rc7 (HEAD at v7.1-rc7) with KASAN_INLINE + TIPC + TIPC_CRYPTO
and reproduced the UAF live. The workload is the same as on 6.12.92: a UDP
bearer with a cluster key is flooded with crafted encrypted frames from an
unknown peer, taking the cluster-key (pick_tx) RX decrypt path, while the
bearer's netns is repeatedly torn down. Decoded against the rc7 vmlinux:

BUG: KASAN: slab-use-after-free in tipc_aead_decrypt_done (net/tipc/crypto.c:999)
Read of size 8 at addr ffff8881056258a8 by task kworker/u16:2/51
CPU: 2 UID: 0 PID: 51 Comm: kworker/u16:2 Not tainted 7.1.0-rc7-00020-... #15
Workqueue: events_unbound
Call Trace:
 <TASK>
 dump_stack_lvl (lib/dump_stack.c:94 lib/dump_stack.c:120)
 print_report (mm/kasan/report.c:378 mm/kasan/report.c:482)
 kasan_report (mm/kasan/report.c:595)
 tipc_aead_decrypt_done (net/tipc/crypto.c:999)
 process_one_work (kernel/workqueue.c:3314)
 worker_thread (kernel/workqueue.c:3397 kernel/workqueue.c:3478)
 kthread (kernel/kthread.c:436)
 ret_from_fork (arch/x86/kernel/process.c:158)
 ret_from_fork_asm (arch/x86/entry/entry_64.S:245)
 </TASK>

Allocated by task 169:
 __kasan_kmalloc (mm/kasan/common.c:398 mm/kasan/common.c:415)
 tipc_crypto_start (net/tipc/crypto.c:1502)
 tipc_init_net (net/tipc/core.c:72)
 ops_init (net/core/net_namespace.c:137)
 setup_net (net/core/net_namespace.c:446)
 copy_net_ns (net/core/net_namespace.c:579)
 create_new_namespaces (kernel/nsproxy.c:132)
 unshare_nsproxy_namespaces (kernel/nsproxy.c:234)
 ksys_unshare (kernel/fork.c:3242)
 __x64_sys_unshare (kernel/fork.c:3316)
 do_syscall_64 (arch/x86/entry/syscall_64.c:63)
 entry_SYSCALL_64_after_hwframe (arch/x86/entry/entry_64.S:121)

Freed by task 8:
 kfree (mm/slub.c:6566)
 tipc_exit_net (net/tipc/core.c:119)
 ops_undo_list (net/core/net_namespace.c)
 cleanup_net (net/core/net_namespace.c:704)
 process_one_work (kernel/workqueue.c:3314)
 worker_thread (kernel/workqueue.c)
 kthread (kernel/kthread.c:436)

The freed object is the per-netns struct tipc_crypto allocated in
tipc_crypto_start() at netns creation (crypto.c:1502 on rc7); the async decrypt
completion then reads aead->crypto->stats from it (crypto.c:999) after
cleanup_net() -> tipc_exit_net() -> tipc_crypto_stop() has freed it -- the exact
read/alloc/free triple this patch closes, now on 7.1-rc7 rather than 6.12.92.

One note on the harness: on x86 the in-tree gcm(aes) the SIMD aead wrapper used
to register via simd_register_aeads_compat() is, as of the aesni rewrite, now
registered directly with crypto_register_aeads() and decrypts synchronously, so
the cryptd async window the original 6.12.92 splat used does not arise from the
stock aesni path on rc7. To exercise the same async completion the changelog
describes, I forced tipc_aead_decrypt()'s completion onto a workqueue in my test
tree; the unguarded aead->crypto dereference in tipc_aead_decrypt_done() is what
KASAN catches, and that code is byte-for-byte the unpatched upstream path. The
source state is in any case unambiguous: tipc_aead_decrypt() on rc7 still lacks
maybe_get_net(aead->crypto->net), so the completion can outlive the free on any
config where crypto_aead_decrypt() goes async (e.g. cryptd offload).

Reproduced under KASAN on both v6.12.92 and v7.1-rc7; the decrypt path lacks the
guard on the latest net tree.

Thanks,
Doruk

  reply	other threads:[~2026-06-15  0:22 UTC|newest]

Thread overview: 4+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-06-10 20:03 [PATCH net v2] tipc: fix slab-use-after-free Read in tipc_aead_decrypt_done Doruk Tan Ozturk
2026-06-11  6:34 ` Tung Quang Nguyen
2026-06-15  0:22   ` Doruk Tan Ozturk [this message]
2026-06-15  6:54     ` Tung Quang Nguyen

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=20260615002211.90694-1-doruk@0sec.ai \
    --to=doruk@0sec.ai \
    --cc=aleksander.lobakin@intel.com \
    --cc=davem@davemloft.net \
    --cc=edumazet@google.com \
    --cc=horms@kernel.org \
    --cc=jmaloy@redhat.com \
    --cc=kuba@kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=netdev@vger.kernel.org \
    --cc=pabeni@redhat.com \
    --cc=tipc-discussion@lists.sourceforge.net \
    --cc=tung.quang.nguyen@est.tech \
    /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