CVE-2026-90302: ocfs2: synchronize heartbeat callbacks with o2net teardown
In the Linux kernel, the following vulnerability has been resolved:
ocfs2: synchronize heartbeat callbacks with o2net teardown
Patch series "ocfs2: harden heartbeat teardown races".
This series fixes two OCFS2 heartbeat/o2net teardown races found by KASAN.
This patch (of 2):
Heartbeat callbacks stay registered while configfs local-node teardown enters o2netstoplistening(). A node-down event can still run through o2netdisconnectnode() and o2netsetnnstate() while teardown is destroying o2netwq, so the later queue/flush operations can hit a dead workqueue. KASAN has caught this as a slab-use-after-free in queuework() with the call chain:
KASAN slab-use-after-free in queuework+0x56/0xa90 Read of size 4 Call trace: dumpstacklvl+0x66/0xa0 printreport+0xce/0x630 queuework+0x56/0xa90 srsoaliasreturnthunk+0x5/0xfbef5 virtaddrvalid+0x19f/0x330 kasanreport+0xe0/0x110 queuedelayedwork+0x58/0x1e0 queuedelayedworkon+0xb4/0xc0 o2netsetnnstate+0x467/0x840 o2netdisconnectnode+0x7b/0xe0 o2nethbnodedowncb+0x54/0x60 o2hbruneventlist+0x236/0x2d0 o2hbcheckslot+0xad4/0xbc0 lockrelease+0xc8/0x290 o2hbcheckslot+0x9ea/0xbc0 tracehardirqson+0x18/0x130 o2hbdodiskheartbeat+0x646/0xb30 (fs/ocfs2/cluster/heartbeat.c:1079) lockacquire+0x466/0x2260 lockdephardirqsonprepare+0xea/0x1a0 ktimegetwithoffset+0xe9/0x230 o2hbthread+0x14e/0x770 kthread+0x1ad/0x1f0 retfromfork+0x3c9/0x540 switchto+0x2e9/0x730 retfromforkasm+0x1a/0x30 Allocated by task stack: kasansavestack+0x33/0x60 kasansavetrack+0x14/0x30 kasankmalloc+0xaa/0xb0 kmallocnoprof+0x292/0x760 allocworkqueue+0x736/0xc60 allocworkqueuenoprof+0xb1/0x110 o2netstartlistening+0xe5/0x430 o2nmnodelocalstore+0x184/0x310 configfswriteiter+0x18a/0x210 vfswrite+0x469/0x810 ksyswrite+0xd2/0x170 dosyscall64+0x115/0x6a0 (arch/x86/entry/syscall64.c:87) entrySYSCALL64afterhwframe+0x77/0x7f Freed by task stack: kasansavestack+0x33/0x60 kasansavetrack+0x14/0x30 kasansavefreeinfo+0x3b/0x60 kasanslabfree+0x5f/0x80 kfree+0x313/0x590 rcucore+0x4f4/0x1320 handlesoftirqs+0x156/0x660
queuedelayedworkon o2netsetnnstate o2netdisconnectnode o2nethbnodedowncb o2hbruneventlist
Keep heartbeat callbacks registered so quorum state still tracks node state, but stop them from driving o2net reconnect/disconnect work once local teardown starts. Mark the transport offline before destroying o2netwq, wait for any in-flight heartbeat callback to finish, and delay bring-up replay until the new local node is published through o2nmthisnode().
The replay also has to stay serialized with heartbeat callback delivery. Otherwise a live-node snapshot can be copied, a real hbdown callback can install -ENOTCONN for a peer, and the stale replay can call o2nethbnodeup() for that same peer and queue reconnect work even though heartbeat is already down.
The buggy scenario involves two paths, with each column showing the order within that path:
local-node teardown: heartbeat node-down callback: 1. configfs local-off enters 1. o2hbruneventlist() invokes o2netstoplistening(). o2nethbnodedowncb(). 2. teardown heads for 2. the callback reaches destroyworkqueue(o2netwq). o2netdisconnectnode() and o2netsetnnstate(). 3. teardown destroys and NULLs 3. the callback flushes or queues o2netwq. work through o2netwq.
Affected Software
Remediation
Recommended actions to resolve this vulnerability, in priority order.
- Upgrade
Upgrade
ocfs2to a version that resolves this vulnerability.Patch ocfs2: harden heartbeat teardown races - Compensating control
Ensure heartbeat callbacks do not drive o2net reconnect/disconnect work after local-node teardown by synchronizing heartbeat callbacks with o2net teardown (keep heartbeat callbacks registered for quorum state tracking, but mark the transport offline before destroying o2net teardown structures).